📅  最后修改于: 2023-12-03 15:42:11.759000             🧑  作者: Mango
本篇文章是 "GATE CS 2018 简体中文" 的第31章,主要内容是关于算法和数据结构的。本章主要介绍了一些基本的算法和数据结构,如搜索、排序、树、哈希表等。
本章介绍的算法包括:
线性搜索是一种简单的算法,它从列表的一个元素开始,按顺序检查每个元素,直到找到所需的元素或列表末尾。线性搜索的代码实现如下:
def linear_search(lst, value):
for i in range(len(lst)):
if lst[i] == value:
return i
return -1 # 如果未找到,则返回-1
二分搜索是一种比线性搜索更快的算法。它的前提是,列表中的元素必须已经排好序。二分搜索将列表中间的元素与要查找的元素进行比较,如果它们相等,则返回该元素的索引;如果要查找的元素小于中间元素,则在列表的左半边继续搜索;否则,在列表的右半边继续搜索。二分搜索的代码实现如下:
def binary_search(lst, value):
low, high = 0, len(lst) - 1
while low <= high:
mid = (low + high) // 2
if value == lst[mid]:
return mid
elif value < lst[mid]:
high = mid - 1
else:
low = mid + 1
return -1 # 如果未找到,则返回-1
冒泡排序是一种比较简单但效率较低的排序算法。它的基本原理是,每次比较相邻两个元素,如果它们的顺序不对,则交换它们。通过多次这样的比较和交换,最大的元素会“冒泡”到列表的末尾。冒泡排序的代码实现如下:
def bubble_sort(lst):
for i in range(len(lst)):
for j in range(len(lst) - 1, i, -1):
if lst[j] < lst[j-1]:
lst[j], lst[j-1] = lst[j-1], lst[j]
归并排序是一种比较高效的排序算法。它的基本原理是,将列表分成大小相等的两个子列表,然后递归地排序这两个子列表,并合并它们以获得排序的列表。归并排序的代码实现如下:
def merge_sort(lst):
if len(lst) > 1:
mid = len(lst) // 2
left_half = lst[:mid]
right_half = lst[mid:]
merge_sort(left_half)
merge_sort(right_half)
i = 0
j = 0
k = 0
while i < len(left_half) and j < len(right_half):
if left_half[i] < right_half[j]:
lst[k] = left_half[i]
i += 1
else:
lst[k] = right_half[j]
j += 1
k += 1
while i < len(left_half):
lst[k] = left_half[i]
i += 1
k += 1
while j < len(right_half):
lst[k] = right_half[j]
j += 1
k += 1
快速排序是一种比较高效的排序算法。它的基本原理是,选择一个基准元素,然后将列表中小于基准元素的元素移到基准元素的左边,将大于基准元素的元素移到基准元素的右边。然后递归地对左右两边的列表进行排序。快速排序的代码实现如下:
def quick_sort(lst, low, high):
if low < high:
p = partition(lst, low, high)
quick_sort(lst, low, p - 1)
quick_sort(lst, p + 1, high)
def partition(lst, low, high):
pivot = lst[high]
i = low - 1
for j in range(low, high):
if lst[j] <= pivot:
i += 1
lst[i], lst[j] = lst[j], lst[i]
lst[i+1], lst[high] = lst[high], lst[i+1]
return i + 1
本章介绍的数据结构包括:
队列是一种基本的数据结构,它的特点是“先进先出”(FIFO)。队列有两个基本操作:入队(enqueue)和出队(dequeue)。队列的代码实现如下:
class Queue:
def __init__(self):
self.items = []
def is_empty(self):
return self.items == []
def enqueue(self, item):
self.items.append(item)
def dequeue(self):
return self.items.pop(0)
栈也是一种基本的数据结构,它的特点是“后进先出”(LIFO)。栈有两个基本操作:入栈(push)和出栈(pop)。栈的代码实现如下:
class Stack:
def __init__(self):
self.items = []
def is_empty(self):
return self.items == []
def push(self, item):
self.items.append(item)
def pop(self):
return self.items.pop()
链表是一种基本的数据结构。它由一系列节点组成,每个节点包含一个数据元素和一个指向下一个节点的指针。链表有两种基本类型:单链表和双链表。链表的代码实现如下:
class Node:
def __init__(self, data=None):
self.data = data
self.next = None
class LinkedList:
def __init__(self):
self.head = None
def is_empty(self):
return self.head == None
def append(self, data):
new_node = Node(data)
if self.head == None:
self.head = new_node
return
current_node = self.head
while current_node.next != None:
current_node = current_node.next
current_node.next = new_node
def delete(self, data):
current_node = self.head
previous_node = None
while current_node != None:
if current_node.data == data:
if previous_node == None:
self.head = current_node.next
else:
previous_node.next = current_node.next
return
previous_node = current_node
current_node = current_node.next
树是一种高效的数据结构,由一系列节点组成,每个节点包含一个数据元素和一个指向其子节点的指针。树有多种形式,常见的包括二叉树、堆和树结构。树的代码实现如下:
class TreeNode:
def __init__(self, data=None):
self.data = data
self.left = None
self.right = None
class BinaryTree:
def __init__(self):
self.root = None
def insert(self, data):
new_node = TreeNode(data)
if self.root == None:
self.root = new_node
return
queue = []
queue.append(self.root)
while queue:
current_node = queue.pop(0)
if current_node.left == None:
current_node.left = new_node
return
elif current_node.right == None:
current_node.right = new_node
return
else:
queue.append(current_node.left)
queue.append(current_node.right)
def delete(self, data):
if self.root == None:
return
if self.root.left == None and self.root.right == None:
if self.root.data == data:
self.root = None
else:
return
key_node = None
queue = []
queue.append(self.root)
while queue:
current_node = queue.pop(0)
if current_node.data == data:
key_node = current_node
if current_node.left != None:
queue.append(current_node.left)
if current_node.right != None:
queue.append(current_node.right)
if key_node != None:
x = current_node.data
self.delete_node(current_node)
key_node.data = x
def delete_node(self, node):
queue = []
queue.append(self.root)
while queue:
current_node = queue.pop(0)
if current_node == node:
current_node = None
return
if current_node.right != None:
if current_node.right == node:
current_node.right = None
return
else:
queue.append(current_node.right)
if current_node.left != None:
if current_node.left == node:
current_node.left = None
return
else:
queue.append(current_node.left)
哈希表是一种高效的数据结构,它可以像数组一样快速访问数据,但不需要预先知道数组的大小。哈希表的实现基于散列函数,根据数据的键计算出一个索引,将数据存储在该索引处。哈希表的代码实现如下:
class HashTable:
def __init__(self):
self.size = 10
self.slots = [None] * self.size
self.data = [None] * self.size
def put(self, key, data):
hash_value = self.hash_function(key)
if self.slots[hash_value] == None:
self.slots[hash_value] = key
self.data[hash_value] = data
else:
if self.slots[hash_value] == key:
self.data[hash_value] = data # 更新旧数据
else:
next_slot = self.rehash(hash_value)
while self.slots[next_slot] != None and \
self.slots[next_slot] != key:
next_slot = self.rehash(next_slot)
if self.slots[next_slot] == None:
self.slots[next_slot] = key
self.data[next_slot] = data
else:
self.data[next_slot] = data # 更新旧数据
def hash_function(self, key):
return key % self.size
def rehash(self, old_hash):
return (old_hash + 1) % self.size
def get(self, key):
hash_value = self.hash_function(key)
if self.slots[hash_value] == key:
return self.data[hash_value]
else:
next_slot = self.rehash(hash_value)
while self.slots[next_slot] != None and \
self.slots[next_slot] != key:
next_slot = self.rehash(next_slot)
if self.slots[next_slot] == key:
return self.data[next_slot]
else:
return None
本章介绍了一些基本的算法和数据结构,包括搜索、排序、队列、栈、链表、树和哈希表。了解这些算法和数据结构对于理解计算机科学和算法分析是非常重要的。