Add typing annotations to Python codes. (#411)
This commit is contained in:
parent
2029d2b939
commit
9151eaf533
@ -8,7 +8,7 @@ import sys, os.path as osp
|
|||||||
sys.path.append(osp.dirname(osp.dirname(osp.abspath(__file__))))
|
sys.path.append(osp.dirname(osp.dirname(osp.abspath(__file__))))
|
||||||
from modules import *
|
from modules import *
|
||||||
|
|
||||||
def random_access(nums):
|
def random_access(nums: List[int]) -> int:
|
||||||
""" 随机访问元素 """
|
""" 随机访问元素 """
|
||||||
# 在区间 [0, len(nums)-1] 中随机抽取一个数字
|
# 在区间 [0, len(nums)-1] 中随机抽取一个数字
|
||||||
random_index = random.randint(0, len(nums) - 1)
|
random_index = random.randint(0, len(nums) - 1)
|
||||||
@ -18,7 +18,7 @@ def random_access(nums):
|
|||||||
|
|
||||||
# 请注意,Python 的 list 是动态数组,可以直接扩展
|
# 请注意,Python 的 list 是动态数组,可以直接扩展
|
||||||
# 为了方便学习,本函数将 list 看作是长度不可变的数组
|
# 为了方便学习,本函数将 list 看作是长度不可变的数组
|
||||||
def extend(nums, enlarge):
|
def extend(nums: List[int], enlarge: int) -> List[int]:
|
||||||
""" 扩展数组长度 """
|
""" 扩展数组长度 """
|
||||||
# 初始化一个扩展长度后的数组
|
# 初始化一个扩展长度后的数组
|
||||||
res = [0] * (len(nums) + enlarge)
|
res = [0] * (len(nums) + enlarge)
|
||||||
@ -28,7 +28,7 @@ def extend(nums, enlarge):
|
|||||||
# 返回扩展后的新数组
|
# 返回扩展后的新数组
|
||||||
return res
|
return res
|
||||||
|
|
||||||
def insert(nums, num, index):
|
def insert(nums: List[int], num: int, index: int) -> None:
|
||||||
""" 在数组的索引 index 处插入元素 num """
|
""" 在数组的索引 index 处插入元素 num """
|
||||||
# 把索引 index 以及之后的所有元素向后移动一位
|
# 把索引 index 以及之后的所有元素向后移动一位
|
||||||
for i in range(len(nums) - 1, index, -1):
|
for i in range(len(nums) - 1, index, -1):
|
||||||
@ -36,13 +36,13 @@ def insert(nums, num, index):
|
|||||||
# 将 num 赋给 index 处元素
|
# 将 num 赋给 index 处元素
|
||||||
nums[index] = num
|
nums[index] = num
|
||||||
|
|
||||||
def remove(nums, index):
|
def remove(nums: List[int], index: int) -> None:
|
||||||
""" 删除索引 index 处元素 """
|
""" 删除索引 index 处元素 """
|
||||||
# 把索引 index 之后的所有元素向前移动一位
|
# 把索引 index 之后的所有元素向前移动一位
|
||||||
for i in range(index, len(nums) - 1):
|
for i in range(index, len(nums) - 1):
|
||||||
nums[i] = nums[i + 1]
|
nums[i] = nums[i + 1]
|
||||||
|
|
||||||
def traverse(nums):
|
def traverse(nums: List[int]) -> None:
|
||||||
""" 遍历数组 """
|
""" 遍历数组 """
|
||||||
count = 0
|
count = 0
|
||||||
# 通过索引遍历数组
|
# 通过索引遍历数组
|
||||||
@ -52,28 +52,27 @@ def traverse(nums):
|
|||||||
for num in nums:
|
for num in nums:
|
||||||
count += 1
|
count += 1
|
||||||
|
|
||||||
def find(nums, target):
|
def find(nums: List[int], target: int) -> int:
|
||||||
""" 在数组中查找指定元素 """
|
""" 在数组中查找指定元素 """
|
||||||
for i in range(len(nums)):
|
for i in range(len(nums)):
|
||||||
if nums[i] == target:
|
if nums[i] == target:
|
||||||
return i
|
return i
|
||||||
return -1
|
return -1
|
||||||
|
|
||||||
|
|
||||||
""" Driver Code """
|
""" Driver Code """
|
||||||
if __name__ == "__main__":
|
if __name__ == "__main__":
|
||||||
""" 初始化数组 """
|
""" 初始化数组 """
|
||||||
arr = [0] * 5
|
arr: List[int] = [0] * 5
|
||||||
print("数组 arr =", arr)
|
print("数组 arr =", arr)
|
||||||
nums = [1, 3, 2, 5, 4]
|
nums: List[int] = [1, 3, 2, 5, 4]
|
||||||
print("数组 nums =", nums)
|
print("数组 nums =", nums)
|
||||||
|
|
||||||
""" 随机访问 """
|
""" 随机访问 """
|
||||||
random_num = random_access(nums)
|
random_num: int = random_access(nums)
|
||||||
print("在 nums 中获取随机元素", random_num)
|
print("在 nums 中获取随机元素", random_num)
|
||||||
|
|
||||||
""" 长度扩展 """
|
""" 长度扩展 """
|
||||||
nums = extend(nums, 3)
|
nums: List[int] = extend(nums, 3)
|
||||||
print("将数组长度扩展至 8 ,得到 nums =", nums)
|
print("将数组长度扩展至 8 ,得到 nums =", nums)
|
||||||
|
|
||||||
""" 插入元素 """
|
""" 插入元素 """
|
||||||
@ -88,5 +87,5 @@ if __name__ == "__main__":
|
|||||||
traverse(nums)
|
traverse(nums)
|
||||||
|
|
||||||
""" 查找元素 """
|
""" 查找元素 """
|
||||||
index = find(nums, 3)
|
index: int = find(nums, 3)
|
||||||
print("在 nums 中查找元素 3 ,得到索引 =", index)
|
print("在 nums 中查找元素 3 ,得到索引 =", index)
|
||||||
|
@ -8,13 +8,13 @@ import sys, os.path as osp
|
|||||||
sys.path.append(osp.dirname(osp.dirname(osp.abspath(__file__))))
|
sys.path.append(osp.dirname(osp.dirname(osp.abspath(__file__))))
|
||||||
from modules import *
|
from modules import *
|
||||||
|
|
||||||
def insert(n0, P):
|
def insert(n0: ListNode, P: ListNode) -> None:
|
||||||
""" 在链表的结点 n0 之后插入结点 P """
|
""" 在链表的结点 n0 之后插入结点 P """
|
||||||
n1 = n0.next
|
n1 = n0.next
|
||||||
P.next = n1
|
P.next = n1
|
||||||
n0.next = P
|
n0.next = P
|
||||||
|
|
||||||
def remove(n0):
|
def remove(n0: ListNode) -> None:
|
||||||
""" 删除链表的结点 n0 之后的首个结点 """
|
""" 删除链表的结点 n0 之后的首个结点 """
|
||||||
if not n0.next:
|
if not n0.next:
|
||||||
return
|
return
|
||||||
@ -23,7 +23,7 @@ def remove(n0):
|
|||||||
n1 = P.next
|
n1 = P.next
|
||||||
n0.next = n1
|
n0.next = n1
|
||||||
|
|
||||||
def access(head, index):
|
def access(head: ListNode, index: int) -> Optional[ListNode]:
|
||||||
""" 访问链表中索引为 index 的结点 """
|
""" 访问链表中索引为 index 的结点 """
|
||||||
for _ in range(index):
|
for _ in range(index):
|
||||||
if not head:
|
if not head:
|
||||||
@ -31,7 +31,7 @@ def access(head, index):
|
|||||||
head = head.next
|
head = head.next
|
||||||
return head
|
return head
|
||||||
|
|
||||||
def find(head, target):
|
def find(head: ListNode, target: int) -> int:
|
||||||
""" 在链表中查找值为 target 的首个结点 """
|
""" 在链表中查找值为 target 的首个结点 """
|
||||||
index = 0
|
index = 0
|
||||||
while head:
|
while head:
|
||||||
@ -70,9 +70,9 @@ if __name__ == "__main__":
|
|||||||
print_linked_list(n0)
|
print_linked_list(n0)
|
||||||
|
|
||||||
""" 访问结点 """
|
""" 访问结点 """
|
||||||
node = access(n0, 3)
|
node: ListNode = access(n0, 3)
|
||||||
print("链表中索引 3 处的结点的值 = {}".format(node.val))
|
print("链表中索引 3 处的结点的值 = {}".format(node.val))
|
||||||
|
|
||||||
""" 查找结点 """
|
""" 查找结点 """
|
||||||
index = find(n0, 2)
|
index: int = find(n0, 2)
|
||||||
print("链表中值为 2 的结点的索引 = {}".format(index))
|
print("链表中值为 2 的结点的索引 = {}".format(index))
|
||||||
|
@ -12,11 +12,11 @@ from modules import *
|
|||||||
""" Driver Code """
|
""" Driver Code """
|
||||||
if __name__ == "__main__":
|
if __name__ == "__main__":
|
||||||
""" 初始化列表 """
|
""" 初始化列表 """
|
||||||
list = [1, 3, 2, 5, 4]
|
list: List[int] = [1, 3, 2, 5, 4]
|
||||||
print("列表 list =", list)
|
print("列表 list =", list)
|
||||||
|
|
||||||
""" 访问元素 """
|
""" 访问元素 """
|
||||||
num = list[1]
|
num: int = list[1]
|
||||||
print("访问索引 1 处的元素,得到 num =", num)
|
print("访问索引 1 处的元素,得到 num =", num)
|
||||||
|
|
||||||
""" 更新元素 """
|
""" 更新元素 """
|
||||||
@ -44,17 +44,17 @@ if __name__ == "__main__":
|
|||||||
print("删除索引 3 处的元素,得到 list =", list)
|
print("删除索引 3 处的元素,得到 list =", list)
|
||||||
|
|
||||||
""" 通过索引遍历列表 """
|
""" 通过索引遍历列表 """
|
||||||
count = 0
|
count: int = 0
|
||||||
for i in range(len(list)):
|
for i in range(len(list)):
|
||||||
count += 1
|
count += 1
|
||||||
|
|
||||||
""" 直接遍历列表元素 """
|
""" 直接遍历列表元素 """
|
||||||
count = 0
|
count: int = 0
|
||||||
for n in list:
|
for n in list:
|
||||||
count += 1
|
count += 1
|
||||||
|
|
||||||
""" 拼接两个列表 """
|
""" 拼接两个列表 """
|
||||||
list1 = [6, 8, 7, 10, 9]
|
list1: List[int] = [6, 8, 7, 10, 9]
|
||||||
list += list1
|
list += list1
|
||||||
print("将列表 list1 拼接到 list 之后,得到 list =", list)
|
print("将列表 list1 拼接到 list 之后,得到 list =", list)
|
||||||
|
|
||||||
|
@ -12,31 +12,31 @@ class MyList:
|
|||||||
""" 列表类简易实现 """
|
""" 列表类简易实现 """
|
||||||
def __init__(self):
|
def __init__(self):
|
||||||
""" 构造方法 """
|
""" 构造方法 """
|
||||||
self.__capacity = 10 # 列表容量
|
self.__capacity: int = 10 # 列表容量
|
||||||
self.__nums = [0] * self.__capacity # 数组(存储列表元素)
|
self.__nums: List[int] = [0] * self.__capacity # 数组(存储列表元素)
|
||||||
self.__size = 0 # 列表长度(即当前元素数量)
|
self.__size: int = 0 # 列表长度(即当前元素数量)
|
||||||
self.__extend_ratio = 2 # 每次列表扩容的倍数
|
self.__extend_ratio: int = 2 # 每次列表扩容的倍数
|
||||||
|
|
||||||
def size(self):
|
def size(self) -> int:
|
||||||
""" 获取列表长度(即当前元素数量) """
|
""" 获取列表长度(即当前元素数量) """
|
||||||
return self.__size
|
return self.__size
|
||||||
|
|
||||||
def capacity(self):
|
def capacity(self) -> int:
|
||||||
""" 获取列表容量 """
|
""" 获取列表容量 """
|
||||||
return self.__capacity
|
return self.__capacity
|
||||||
|
|
||||||
def get(self, index):
|
def get(self, index: int) -> int:
|
||||||
""" 访问元素 """
|
""" 访问元素 """
|
||||||
# 索引如果越界则抛出异常,下同
|
# 索引如果越界则抛出异常,下同
|
||||||
assert index >= 0 and index < self.__size, "索引越界"
|
assert index >= 0 and index < self.__size, "索引越界"
|
||||||
return self.__nums[index]
|
return self.__nums[index]
|
||||||
|
|
||||||
def set(self, num, index):
|
def set(self, num: int, index: int) -> None:
|
||||||
""" 更新元素 """
|
""" 更新元素 """
|
||||||
assert index >= 0 and index < self.__size, "索引越界"
|
assert index >= 0 and index < self.__size, "索引越界"
|
||||||
self.__nums[index] = num
|
self.__nums[index] = num
|
||||||
|
|
||||||
def add(self, num):
|
def add(self, num: int) -> None:
|
||||||
""" 尾部添加元素 """
|
""" 尾部添加元素 """
|
||||||
# 元素数量超出容量时,触发扩容机制
|
# 元素数量超出容量时,触发扩容机制
|
||||||
if self.size() == self.capacity():
|
if self.size() == self.capacity():
|
||||||
@ -44,7 +44,7 @@ class MyList:
|
|||||||
self.__nums[self.__size] = num
|
self.__nums[self.__size] = num
|
||||||
self.__size += 1
|
self.__size += 1
|
||||||
|
|
||||||
def insert(self, num, index):
|
def insert(self, num: int, index: int) -> None:
|
||||||
""" 中间插入元素 """
|
""" 中间插入元素 """
|
||||||
assert index >= 0 and index < self.__size, "索引越界"
|
assert index >= 0 and index < self.__size, "索引越界"
|
||||||
# 元素数量超出容量时,触发扩容机制
|
# 元素数量超出容量时,触发扩容机制
|
||||||
@ -57,7 +57,7 @@ class MyList:
|
|||||||
# 更新元素数量
|
# 更新元素数量
|
||||||
self.__size += 1
|
self.__size += 1
|
||||||
|
|
||||||
def remove(self, index):
|
def remove(self, index: int) -> int:
|
||||||
""" 删除元素 """
|
""" 删除元素 """
|
||||||
assert index >= 0 and index < self.__size, "索引越界"
|
assert index >= 0 and index < self.__size, "索引越界"
|
||||||
num = self.__nums[index]
|
num = self.__nums[index]
|
||||||
@ -69,14 +69,14 @@ class MyList:
|
|||||||
# 返回被删除元素
|
# 返回被删除元素
|
||||||
return num
|
return num
|
||||||
|
|
||||||
def extend_capacity(self):
|
def extend_capacity(self) -> None:
|
||||||
""" 列表扩容 """
|
""" 列表扩容 """
|
||||||
# 新建一个长度为 self.__size 的数组,并将原数组拷贝到新数组
|
# 新建一个长度为 self.__size 的数组,并将原数组拷贝到新数组
|
||||||
self.__nums = self.__nums + [0] * self.capacity() * (self.__extend_ratio - 1)
|
self.__nums = self.__nums + [0] * self.capacity() * (self.__extend_ratio - 1)
|
||||||
# 更新列表容量
|
# 更新列表容量
|
||||||
self.__capacity = len(self.__nums)
|
self.__capacity = len(self.__nums)
|
||||||
|
|
||||||
def to_array(self):
|
def to_array(self) -> List[int]:
|
||||||
""" 返回有效长度的列表 """
|
""" 返回有效长度的列表 """
|
||||||
return self.__nums[:self.__size]
|
return self.__nums[:self.__size]
|
||||||
|
|
||||||
|
@ -14,7 +14,7 @@ def two_sum_brute_force(nums: List[int], target: int) -> List[int]:
|
|||||||
for i in range(len(nums) - 1):
|
for i in range(len(nums) - 1):
|
||||||
for j in range(i + 1, len(nums)):
|
for j in range(i + 1, len(nums)):
|
||||||
if nums[i] + nums[j] == target:
|
if nums[i] + nums[j] == target:
|
||||||
return i, j
|
return [i, j]
|
||||||
return []
|
return []
|
||||||
|
|
||||||
def two_sum_hash_table(nums: List[int], target: int) -> List[int]:
|
def two_sum_hash_table(nums: List[int], target: int) -> List[int]:
|
||||||
@ -24,7 +24,7 @@ def two_sum_hash_table(nums: List[int], target: int) -> List[int]:
|
|||||||
# 单层循环,时间复杂度 O(n)
|
# 单层循环,时间复杂度 O(n)
|
||||||
for i in range(len(nums)):
|
for i in range(len(nums)):
|
||||||
if target - nums[i] in dic:
|
if target - nums[i] in dic:
|
||||||
return dic[target - nums[i]], i
|
return [dic[target - nums[i]], i]
|
||||||
dic[nums[i]] = i
|
dic[nums[i]] = i
|
||||||
return []
|
return []
|
||||||
|
|
||||||
@ -37,8 +37,8 @@ if __name__ == '__main__':
|
|||||||
|
|
||||||
# ====== Driver Code ======
|
# ====== Driver Code ======
|
||||||
# 方法一
|
# 方法一
|
||||||
res = two_sum_brute_force(nums, target)
|
res: List[int] = two_sum_brute_force(nums, target)
|
||||||
print("方法一 res =", res)
|
print("方法一 res =", res)
|
||||||
# 方法二
|
# 方法二
|
||||||
res = two_sum_hash_table(nums, target)
|
res: List[int] = two_sum_hash_table(nums, target)
|
||||||
print("方法二 res =", res)
|
print("方法二 res =", res)
|
||||||
|
@ -8,52 +8,52 @@ import sys, os.path as osp
|
|||||||
sys.path.append(osp.dirname(osp.dirname(osp.abspath(__file__))))
|
sys.path.append(osp.dirname(osp.dirname(osp.abspath(__file__))))
|
||||||
from modules import *
|
from modules import *
|
||||||
|
|
||||||
def function():
|
def function() -> int:
|
||||||
""" 函数 """
|
""" 函数 """
|
||||||
# do something
|
# do something
|
||||||
return 0
|
return 0
|
||||||
|
|
||||||
def constant(n):
|
def constant(n: int) -> None:
|
||||||
""" 常数阶 """
|
""" 常数阶 """
|
||||||
# 常量、变量、对象占用 O(1) 空间
|
# 常量、变量、对象占用 O(1) 空间
|
||||||
a = 0
|
a: int = 0
|
||||||
nums = [0] * 10000
|
nums: List[int] = [0] * 10000
|
||||||
node = ListNode(0)
|
node = ListNode(0)
|
||||||
# 循环中的变量占用 O(1) 空间
|
# 循环中的变量占用 O(1) 空间
|
||||||
for _ in range(n):
|
for _ in range(n):
|
||||||
c = 0
|
c: int = 0
|
||||||
# 循环中的函数占用 O(1) 空间
|
# 循环中的函数占用 O(1) 空间
|
||||||
for _ in range(n):
|
for _ in range(n):
|
||||||
function()
|
function()
|
||||||
|
|
||||||
def linear(n):
|
def linear(n: int) -> None:
|
||||||
""" 线性阶 """
|
""" 线性阶 """
|
||||||
# 长度为 n 的列表占用 O(n) 空间
|
# 长度为 n 的列表占用 O(n) 空间
|
||||||
nums = [0] * n
|
nums: List[int] = [0] * n
|
||||||
# 长度为 n 的哈希表占用 O(n) 空间
|
# 长度为 n 的哈希表占用 O(n) 空间
|
||||||
mapp = {}
|
mapp: Dict = {}
|
||||||
for i in range(n):
|
for i in range(n):
|
||||||
mapp[i] = str(i)
|
mapp[i] = str(i)
|
||||||
|
|
||||||
def linear_recur(n):
|
def linear_recur(n: int) -> None:
|
||||||
""" 线性阶(递归实现) """
|
""" 线性阶(递归实现) """
|
||||||
print("递归 n =", n)
|
print("递归 n =", n)
|
||||||
if n == 1: return
|
if n == 1: return
|
||||||
linear_recur(n - 1)
|
linear_recur(n - 1)
|
||||||
|
|
||||||
def quadratic(n):
|
def quadratic(n: int) -> None:
|
||||||
""" 平方阶 """
|
""" 平方阶 """
|
||||||
# 二维列表占用 O(n^2) 空间
|
# 二维列表占用 O(n^2) 空间
|
||||||
num_matrix = [[0] * n for _ in range(n)]
|
num_matrix: List[List[int]] = [[0] * n for _ in range(n)]
|
||||||
|
|
||||||
def quadratic_recur(n):
|
def quadratic_recur(n: int) -> int:
|
||||||
""" 平方阶(递归实现) """
|
""" 平方阶(递归实现) """
|
||||||
if n <= 0: return 0
|
if n <= 0: return 0
|
||||||
# 数组 nums 长度为 n, n-1, ..., 2, 1
|
# 数组 nums 长度为 n, n-1, ..., 2, 1
|
||||||
nums = [0] * n
|
nums: List[int] = [0] * n
|
||||||
return quadratic_recur(n - 1)
|
return quadratic_recur(n - 1)
|
||||||
|
|
||||||
def build_tree(n):
|
def build_tree(n: int) -> Optional[TreeNode]:
|
||||||
""" 指数阶(建立满二叉树) """
|
""" 指数阶(建立满二叉树) """
|
||||||
if n == 0: return None
|
if n == 0: return None
|
||||||
root = TreeNode(0)
|
root = TreeNode(0)
|
||||||
@ -74,5 +74,5 @@ if __name__ == "__main__":
|
|||||||
quadratic(n)
|
quadratic(n)
|
||||||
quadratic_recur(n)
|
quadratic_recur(n)
|
||||||
# 指数阶
|
# 指数阶
|
||||||
root = build_tree(n)
|
root: Optional[TreeNode] = build_tree(n)
|
||||||
print_tree(root)
|
print_tree(root)
|
||||||
|
@ -8,56 +8,57 @@ import sys, os.path as osp
|
|||||||
sys.path.append(osp.dirname(osp.dirname(osp.abspath(__file__))))
|
sys.path.append(osp.dirname(osp.dirname(osp.abspath(__file__))))
|
||||||
from modules import *
|
from modules import *
|
||||||
|
|
||||||
def constant(n):
|
def constant(n: int) -> int:
|
||||||
""" 常数阶 """
|
""" 常数阶 """
|
||||||
count = 0
|
count: int = 0
|
||||||
size = 100000
|
size: int = 100000
|
||||||
for _ in range(size):
|
for _ in range(size):
|
||||||
count += 1
|
count += 1
|
||||||
return count
|
return count
|
||||||
|
|
||||||
def linear(n):
|
def linear(n: int) -> int:
|
||||||
""" 线性阶 """
|
""" 线性阶 """
|
||||||
count = 0
|
count: int = 0
|
||||||
for _ in range(n):
|
for _ in range(n):
|
||||||
count += 1
|
count += 1
|
||||||
return count
|
return count
|
||||||
|
|
||||||
def array_traversal(nums):
|
def array_traversal(nums: List[int]) -> int:
|
||||||
""" 线性阶(遍历数组)"""
|
""" 线性阶(遍历数组)"""
|
||||||
count = 0
|
count: int = 0
|
||||||
# 循环次数与数组长度成正比
|
# 循环次数与数组长度成正比
|
||||||
for num in nums:
|
for num in nums:
|
||||||
count += 1
|
count += 1
|
||||||
return count
|
return count
|
||||||
|
|
||||||
def quadratic(n):
|
def quadratic(n: int) -> int:
|
||||||
""" 平方阶 """
|
""" 平方阶 """
|
||||||
count = 0
|
count: int = 0
|
||||||
# 循环次数与数组长度成平方关系
|
# 循环次数与数组长度成平方关系
|
||||||
for i in range(n):
|
for i in range(n):
|
||||||
for j in range(n):
|
for j in range(n):
|
||||||
count += 1
|
count += 1
|
||||||
return count
|
return count
|
||||||
|
|
||||||
def bubble_sort(nums):
|
def bubble_sort(nums: List[int]) -> int:
|
||||||
""" 平方阶(冒泡排序)"""
|
""" 平方阶(冒泡排序)"""
|
||||||
count = 0 # 计数器
|
count: int = 0 # 计数器
|
||||||
# 外循环:待排序元素数量为 n-1, n-2, ..., 1
|
# 外循环:待排序元素数量为 n-1, n-2, ..., 1
|
||||||
for i in range(len(nums) - 1, 0, -1):
|
for i in range(len(nums) - 1, 0, -1):
|
||||||
# 内循环:冒泡操作
|
# 内循环:冒泡操作
|
||||||
for j in range(i):
|
for j in range(i):
|
||||||
if nums[j] > nums[j + 1]:
|
if nums[j] > nums[j + 1]:
|
||||||
# 交换 nums[j] 与 nums[j + 1]
|
# 交换 nums[j] 与 nums[j + 1]
|
||||||
tmp = nums[j]
|
tmp: int = nums[j]
|
||||||
nums[j] = nums[j + 1]
|
nums[j] = nums[j + 1]
|
||||||
nums[j + 1] = tmp
|
nums[j + 1] = tmp
|
||||||
count += 3 # 元素交换包含 3 个单元操作
|
count += 3 # 元素交换包含 3 个单元操作
|
||||||
return count
|
return count
|
||||||
|
|
||||||
def exponential(n):
|
def exponential(n: int) -> int:
|
||||||
""" 指数阶(循环实现)"""
|
""" 指数阶(循环实现)"""
|
||||||
count, base = 0, 1
|
count: int = 0
|
||||||
|
base: int = 1
|
||||||
# cell 每轮一分为二,形成数列 1, 2, 4, 8, ..., 2^(n-1)
|
# cell 每轮一分为二,形成数列 1, 2, 4, 8, ..., 2^(n-1)
|
||||||
for _ in range(n):
|
for _ in range(n):
|
||||||
for _ in range(base):
|
for _ in range(base):
|
||||||
@ -66,37 +67,37 @@ def exponential(n):
|
|||||||
# count = 1 + 2 + 4 + 8 + .. + 2^(n-1) = 2^n - 1
|
# count = 1 + 2 + 4 + 8 + .. + 2^(n-1) = 2^n - 1
|
||||||
return count
|
return count
|
||||||
|
|
||||||
def exp_recur(n):
|
def exp_recur(n: int) -> int:
|
||||||
""" 指数阶(递归实现)"""
|
""" 指数阶(递归实现)"""
|
||||||
if n == 1: return 1
|
if n == 1: return 1
|
||||||
return exp_recur(n - 1) + exp_recur(n - 1) + 1
|
return exp_recur(n - 1) + exp_recur(n - 1) + 1
|
||||||
|
|
||||||
def logarithmic(n):
|
def logarithmic(n: float) -> int:
|
||||||
""" 对数阶(循环实现)"""
|
""" 对数阶(循环实现)"""
|
||||||
count = 0
|
count: int = 0
|
||||||
while n > 1:
|
while n > 1:
|
||||||
n = n / 2
|
n = n / 2
|
||||||
count += 1
|
count += 1
|
||||||
return count
|
return count
|
||||||
|
|
||||||
def log_recur(n):
|
def log_recur(n: float) -> int:
|
||||||
""" 对数阶(递归实现)"""
|
""" 对数阶(递归实现)"""
|
||||||
if n <= 1: return 0
|
if n <= 1: return 0
|
||||||
return log_recur(n / 2) + 1
|
return log_recur(n / 2) + 1
|
||||||
|
|
||||||
def linear_log_recur(n):
|
def linear_log_recur(n: float) -> int:
|
||||||
""" 线性对数阶 """
|
""" 线性对数阶 """
|
||||||
if n <= 1: return 1
|
if n <= 1: return 1
|
||||||
count = linear_log_recur(n // 2) + \
|
count: int = linear_log_recur(n // 2) + \
|
||||||
linear_log_recur(n // 2)
|
linear_log_recur(n // 2)
|
||||||
for _ in range(n):
|
for _ in range(n):
|
||||||
count += 1
|
count += 1
|
||||||
return count
|
return count
|
||||||
|
|
||||||
def factorial_recur(n):
|
def factorial_recur(n: int) -> int:
|
||||||
""" 阶乘阶(递归实现)"""
|
""" 阶乘阶(递归实现)"""
|
||||||
if n == 0: return 1
|
if n == 0: return 1
|
||||||
count = 0
|
count: int = 0
|
||||||
# 从 1 个分裂出 n 个
|
# 从 1 个分裂出 n 个
|
||||||
for _ in range(n):
|
for _ in range(n):
|
||||||
count += factorial_recur(n - 1)
|
count += factorial_recur(n - 1)
|
||||||
@ -109,32 +110,32 @@ if __name__ == "__main__":
|
|||||||
n = 8
|
n = 8
|
||||||
print("输入数据大小 n =", n)
|
print("输入数据大小 n =", n)
|
||||||
|
|
||||||
count = constant(n)
|
count: int = constant(n)
|
||||||
print("常数阶的计算操作数量 =", count)
|
print("常数阶的计算操作数量 =", count)
|
||||||
|
|
||||||
count = linear(n)
|
count: int = linear(n)
|
||||||
print("线性阶的计算操作数量 =", count)
|
print("线性阶的计算操作数量 =", count)
|
||||||
count = array_traversal([0] * n)
|
count: int = array_traversal([0] * n)
|
||||||
print("线性阶(遍历数组)的计算操作数量 =", count)
|
print("线性阶(遍历数组)的计算操作数量 =", count)
|
||||||
|
|
||||||
count = quadratic(n)
|
count: int = quadratic(n)
|
||||||
print("平方阶的计算操作数量 =", count)
|
print("平方阶的计算操作数量 =", count)
|
||||||
nums = [i for i in range(n, 0, -1)] # [n,n-1,...,2,1]
|
nums: List[int] = [i for i in range(n, 0, -1)] # [n,n-1,...,2,1]
|
||||||
count = bubble_sort(nums)
|
count: int = bubble_sort(nums)
|
||||||
print("平方阶(冒泡排序)的计算操作数量 =", count)
|
print("平方阶(冒泡排序)的计算操作数量 =", count)
|
||||||
|
|
||||||
count = exponential(n)
|
count: int = exponential(n)
|
||||||
print("指数阶(循环实现)的计算操作数量 =", count)
|
print("指数阶(循环实现)的计算操作数量 =", count)
|
||||||
count = exp_recur(n)
|
count: int = exp_recur(n)
|
||||||
print("指数阶(递归实现)的计算操作数量 =", count)
|
print("指数阶(递归实现)的计算操作数量 =", count)
|
||||||
|
|
||||||
count = logarithmic(n)
|
count: int = logarithmic(n)
|
||||||
print("对数阶(循环实现)的计算操作数量 =", count)
|
print("对数阶(循环实现)的计算操作数量 =", count)
|
||||||
count = log_recur(n)
|
count: int = log_recur(n)
|
||||||
print("对数阶(递归实现)的计算操作数量 =", count)
|
print("对数阶(递归实现)的计算操作数量 =", count)
|
||||||
|
|
||||||
count = linear_log_recur(n)
|
count: int = linear_log_recur(n)
|
||||||
print("线性对数阶(递归实现)的计算操作数量 =", count)
|
print("线性对数阶(递归实现)的计算操作数量 =", count)
|
||||||
|
|
||||||
count = factorial_recur(n)
|
count: int = factorial_recur(n)
|
||||||
print("阶乘阶(递归实现)的计算操作数量 =", count)
|
print("阶乘阶(递归实现)的计算操作数量 =", count)
|
||||||
|
@ -8,15 +8,15 @@ import sys, os.path as osp
|
|||||||
sys.path.append(osp.dirname(osp.dirname(osp.abspath(__file__))))
|
sys.path.append(osp.dirname(osp.dirname(osp.abspath(__file__))))
|
||||||
from modules import *
|
from modules import *
|
||||||
|
|
||||||
def random_numbers(n):
|
def random_numbers(n: int) -> List[int]:
|
||||||
""" 生成一个数组,元素为: 1, 2, ..., n ,顺序被打乱 """
|
""" 生成一个数组,元素为: 1, 2, ..., n ,顺序被打乱 """
|
||||||
# 生成数组 nums =: 1, 2, 3, ..., n
|
# 生成数组 nums =: 1, 2, 3, ..., n
|
||||||
nums = [i for i in range(1, n + 1)]
|
nums: List[int] = [i for i in range(1, n + 1)]
|
||||||
# 随机打乱数组元素
|
# 随机打乱数组元素
|
||||||
random.shuffle(nums)
|
random.shuffle(nums)
|
||||||
return nums
|
return nums
|
||||||
|
|
||||||
def find_one(nums):
|
def find_one(nums: List[int]) -> int:
|
||||||
""" 查找数组 nums 中数字 1 所在索引 """
|
""" 查找数组 nums 中数字 1 所在索引 """
|
||||||
for i in range(len(nums)):
|
for i in range(len(nums)):
|
||||||
# 当元素 1 在数组头部时,达到最佳时间复杂度 O(1)
|
# 当元素 1 在数组头部时,达到最佳时间复杂度 O(1)
|
||||||
@ -29,8 +29,8 @@ def find_one(nums):
|
|||||||
""" Driver Code """
|
""" Driver Code """
|
||||||
if __name__ == "__main__":
|
if __name__ == "__main__":
|
||||||
for i in range(10):
|
for i in range(10):
|
||||||
n = 100
|
n: int = 100
|
||||||
nums = random_numbers(n)
|
nums: List[int] = random_numbers(n)
|
||||||
index = find_one(nums)
|
index: int = find_one(nums)
|
||||||
print("\n数组 [ 1, 2, ..., n ] 被打乱后 =", nums)
|
print("\n数组 [ 1, 2, ..., n ] 被打乱后 =", nums)
|
||||||
print("数字 1 的索引为", index)
|
print("数字 1 的索引为", index)
|
||||||
|
@ -10,12 +10,10 @@ from modules import *
|
|||||||
|
|
||||||
class GraphAdjList:
|
class GraphAdjList:
|
||||||
""" 基于邻接表实现的无向图类 """
|
""" 基于邻接表实现的无向图类 """
|
||||||
# 邻接表,key: 顶点,value:该顶点的所有邻接顶点
|
|
||||||
adj_list = {}
|
|
||||||
|
|
||||||
def __init__(self, edges: List[List[Vertex]]) -> None:
|
def __init__(self, edges: List[List[Vertex]]) -> None:
|
||||||
""" 构造方法 """
|
""" 构造方法 """
|
||||||
self.adj_list = {}
|
# 邻接表,key: 顶点,value:该顶点的所有邻接顶点
|
||||||
|
self.adj_list: Dict = {}
|
||||||
# 添加所有顶点和边
|
# 添加所有顶点和边
|
||||||
for edge in edges:
|
for edge in edges:
|
||||||
self.add_vertex(edge[0])
|
self.add_vertex(edge[0])
|
||||||
|
@ -11,14 +11,14 @@ from modules import *
|
|||||||
class GraphAdjMat:
|
class GraphAdjMat:
|
||||||
""" 基于邻接矩阵实现的无向图类 """
|
""" 基于邻接矩阵实现的无向图类 """
|
||||||
# 顶点列表,元素代表“顶点值”,索引代表“顶点索引”
|
# 顶点列表,元素代表“顶点值”,索引代表“顶点索引”
|
||||||
vertices = []
|
vertices: List[int] = []
|
||||||
# 邻接矩阵,行列索引对应“顶点索引”
|
# 邻接矩阵,行列索引对应“顶点索引”
|
||||||
adj_mat = []
|
adj_mat: List[List[int]] = []
|
||||||
|
|
||||||
def __init__(self, vertices, edges):
|
def __init__(self, vertices: List[int], edges: List[List[int]]) -> None:
|
||||||
""" 构造方法 """
|
""" 构造方法 """
|
||||||
self.vertices = []
|
self.vertices: List[int] = []
|
||||||
self.adj_mat = []
|
self.adj_mat: List[List[int]] = []
|
||||||
# 添加顶点
|
# 添加顶点
|
||||||
for val in vertices:
|
for val in vertices:
|
||||||
self.add_vertex(val)
|
self.add_vertex(val)
|
||||||
@ -27,23 +27,23 @@ class GraphAdjMat:
|
|||||||
for e in edges:
|
for e in edges:
|
||||||
self.add_edge(e[0], e[1])
|
self.add_edge(e[0], e[1])
|
||||||
|
|
||||||
def size(self):
|
def size(self) -> int:
|
||||||
""" 获取顶点数量 """
|
""" 获取顶点数量 """
|
||||||
return len(self.vertices)
|
return len(self.vertices)
|
||||||
|
|
||||||
def add_vertex(self, val):
|
def add_vertex(self, val: int) -> None:
|
||||||
""" 添加顶点 """
|
""" 添加顶点 """
|
||||||
n = self.size()
|
n = self.size()
|
||||||
# 向顶点列表中添加新顶点的值
|
# 向顶点列表中添加新顶点的值
|
||||||
self.vertices.append(val)
|
self.vertices.append(val)
|
||||||
# 在邻接矩阵中添加一行
|
# 在邻接矩阵中添加一行
|
||||||
new_row = [0]*n
|
new_row = [0] * n
|
||||||
self.adj_mat.append(new_row)
|
self.adj_mat.append(new_row)
|
||||||
# 在邻接矩阵中添加一列
|
# 在邻接矩阵中添加一列
|
||||||
for row in self.adj_mat:
|
for row in self.adj_mat:
|
||||||
row.append(0)
|
row.append(0)
|
||||||
|
|
||||||
def remove_vertex(self, index):
|
def remove_vertex(self, index: int) -> None:
|
||||||
""" 删除顶点 """
|
""" 删除顶点 """
|
||||||
if index >= self.size():
|
if index >= self.size():
|
||||||
raise IndexError()
|
raise IndexError()
|
||||||
@ -55,7 +55,7 @@ class GraphAdjMat:
|
|||||||
for row in self.adj_mat:
|
for row in self.adj_mat:
|
||||||
row.pop(index)
|
row.pop(index)
|
||||||
|
|
||||||
def add_edge(self, i, j):
|
def add_edge(self, i: int, j: int) -> None:
|
||||||
""" 添加边 """
|
""" 添加边 """
|
||||||
# 参数 i, j 对应 vertices 元素索引
|
# 参数 i, j 对应 vertices 元素索引
|
||||||
# 索引越界与相等处理
|
# 索引越界与相等处理
|
||||||
@ -65,7 +65,7 @@ class GraphAdjMat:
|
|||||||
self.adj_mat[i][j] = 1
|
self.adj_mat[i][j] = 1
|
||||||
self.adj_mat[j][i] = 1
|
self.adj_mat[j][i] = 1
|
||||||
|
|
||||||
def remove_edge(self, i, j):
|
def remove_edge(self, i: int, j: int) -> None:
|
||||||
""" 删除边 """
|
""" 删除边 """
|
||||||
# 参数 i, j 对应 vertices 元素索引
|
# 参数 i, j 对应 vertices 元素索引
|
||||||
# 索引越界与相等处理
|
# 索引越界与相等处理
|
||||||
@ -74,7 +74,7 @@ class GraphAdjMat:
|
|||||||
self.adj_mat[i][j] = 0
|
self.adj_mat[i][j] = 0
|
||||||
self.adj_mat[j][i] = 0
|
self.adj_mat[j][i] = 0
|
||||||
|
|
||||||
def print(self):
|
def print(self) -> None:
|
||||||
""" 打印邻接矩阵 """
|
""" 打印邻接矩阵 """
|
||||||
print("顶点列表 =", self.vertices)
|
print("顶点列表 =", self.vertices)
|
||||||
print("邻接矩阵 =")
|
print("邻接矩阵 =")
|
||||||
@ -85,8 +85,8 @@ class GraphAdjMat:
|
|||||||
if __name__ == "__main__":
|
if __name__ == "__main__":
|
||||||
""" 初始化无向图 """
|
""" 初始化无向图 """
|
||||||
# 请注意,edges 元素代表顶点索引,即对应 vertices 元素索引
|
# 请注意,edges 元素代表顶点索引,即对应 vertices 元素索引
|
||||||
vertices = [1, 3, 2, 5, 4]
|
vertices: List[int] = [1, 3, 2, 5, 4]
|
||||||
edges = [[0, 1], [0, 3], [1, 2], [2, 3], [2, 4], [3, 4]]
|
edges: List[List[int]] = [[0, 1], [0, 3], [1, 2], [2, 3], [2, 4], [3, 4]]
|
||||||
graph = GraphAdjMat(vertices, edges)
|
graph = GraphAdjMat(vertices, edges)
|
||||||
print("\n初始化后,图为")
|
print("\n初始化后,图为")
|
||||||
graph.print()
|
graph.print()
|
||||||
|
@ -4,9 +4,13 @@ Created Time: 2022-12-14
|
|||||||
Author: msk397 (machangxinq@gmail.com)
|
Author: msk397 (machangxinq@gmail.com)
|
||||||
"""
|
"""
|
||||||
|
|
||||||
|
import sys, os.path as osp
|
||||||
|
sys.path.append(osp.dirname(osp.dirname(osp.abspath(__file__))))
|
||||||
|
from modules import *
|
||||||
|
|
||||||
class Entry:
|
class Entry:
|
||||||
""" 键值对 int->String """
|
""" 键值对 int->String """
|
||||||
def __init__(self, key, val):
|
def __init__(self, key: int, val: str):
|
||||||
self.key = key
|
self.key = key
|
||||||
self.val = val
|
self.val = val
|
||||||
|
|
||||||
@ -15,58 +19,58 @@ class ArrayHashMap:
|
|||||||
def __init__(self):
|
def __init__(self):
|
||||||
""" 构造方法 """
|
""" 构造方法 """
|
||||||
# 初始化一个长度为 100 的桶(数组)
|
# 初始化一个长度为 100 的桶(数组)
|
||||||
self.bucket = [None] * 100
|
self.bucket: List[Optional[Entry]] = [None] * 100
|
||||||
|
|
||||||
def hash_func(self, key):
|
def hash_func(self, key: int) -> int:
|
||||||
""" 哈希函数 """
|
""" 哈希函数 """
|
||||||
index = key % 100
|
index: int = key % 100
|
||||||
return index
|
return index
|
||||||
|
|
||||||
def get(self, key):
|
def get(self, key: int) -> str:
|
||||||
""" 查询操作 """
|
""" 查询操作 """
|
||||||
index = self.hash_func(key)
|
index: int = self.hash_func(key)
|
||||||
pair = self.bucket[index]
|
pair: Entry = self.bucket[index]
|
||||||
if pair is None:
|
if pair is None:
|
||||||
return None
|
return None
|
||||||
return pair.val
|
return pair.val
|
||||||
|
|
||||||
def put(self, key, val):
|
def put(self, key: int, val: str) -> None:
|
||||||
""" 添加操作 """
|
""" 添加操作 """
|
||||||
pair = Entry(key, val)
|
pair = Entry(key, val)
|
||||||
index = self.hash_func(key)
|
index: int = self.hash_func(key)
|
||||||
self.bucket[index] = pair
|
self.bucket[index] = pair
|
||||||
|
|
||||||
def remove(self, key):
|
def remove(self, key: int) -> None:
|
||||||
""" 删除操作 """
|
""" 删除操作 """
|
||||||
index = self.hash_func(key)
|
index: int = self.hash_func(key)
|
||||||
# 置为 None ,代表删除
|
# 置为 None ,代表删除
|
||||||
self.bucket[index] = None
|
self.bucket[index] = None
|
||||||
|
|
||||||
def entry_set(self):
|
def entry_set(self) -> List[Entry]:
|
||||||
""" 获取所有键值对 """
|
""" 获取所有键值对 """
|
||||||
result = []
|
result: List[Entry] = []
|
||||||
for pair in self.bucket:
|
for pair in self.bucket:
|
||||||
if pair is not None:
|
if pair is not None:
|
||||||
result.append(pair)
|
result.append(pair)
|
||||||
return result
|
return result
|
||||||
|
|
||||||
def key_set(self):
|
def key_set(self) -> List[int]:
|
||||||
""" 获取所有键 """
|
""" 获取所有键 """
|
||||||
result = []
|
result: List[int] = []
|
||||||
for pair in self.bucket:
|
for pair in self.bucket:
|
||||||
if pair is not None:
|
if pair is not None:
|
||||||
result.append(pair.key)
|
result.append(pair.key)
|
||||||
return result
|
return result
|
||||||
|
|
||||||
def value_set(self):
|
def value_set(self) -> List[str]:
|
||||||
""" 获取所有值 """
|
""" 获取所有值 """
|
||||||
result = []
|
result: List[str] = []
|
||||||
for pair in self.bucket:
|
for pair in self.bucket:
|
||||||
if pair is not None:
|
if pair is not None:
|
||||||
result.append(pair.val)
|
result.append(pair.val)
|
||||||
return result
|
return result
|
||||||
|
|
||||||
def print(self):
|
def print(self) -> None:
|
||||||
""" 打印哈希表 """
|
""" 打印哈希表 """
|
||||||
for pair in self.bucket:
|
for pair in self.bucket:
|
||||||
if pair is not None:
|
if pair is not None:
|
||||||
|
@ -12,7 +12,7 @@ from modules import *
|
|||||||
""" Driver Code """
|
""" Driver Code """
|
||||||
if __name__ == "__main__":
|
if __name__ == "__main__":
|
||||||
""" 初始化哈希表 """
|
""" 初始化哈希表 """
|
||||||
mapp = {}
|
mapp: Dict = {}
|
||||||
|
|
||||||
""" 添加操作 """
|
""" 添加操作 """
|
||||||
# 在哈希表中添加键值对 (key, value)
|
# 在哈希表中添加键值对 (key, value)
|
||||||
@ -26,7 +26,7 @@ if __name__ == "__main__":
|
|||||||
|
|
||||||
""" 查询操作 """
|
""" 查询操作 """
|
||||||
# 向哈希表输入键 key ,得到值 value
|
# 向哈希表输入键 key ,得到值 value
|
||||||
name = mapp[15937]
|
name: str = mapp[15937]
|
||||||
print("\n输入学号 15937 ,查询到姓名 " + name)
|
print("\n输入学号 15937 ,查询到姓名 " + name)
|
||||||
|
|
||||||
""" 删除操作 """
|
""" 删除操作 """
|
||||||
|
@ -4,16 +4,18 @@ Created Time: 2023-02-23
|
|||||||
Author: Krahets (krahets@163.com)
|
Author: Krahets (krahets@163.com)
|
||||||
"""
|
"""
|
||||||
|
|
||||||
import sys, os.path as osp
|
import sys
|
||||||
|
import os.path as osp
|
||||||
sys.path.append(osp.dirname(osp.dirname(osp.abspath(__file__))))
|
sys.path.append(osp.dirname(osp.dirname(osp.abspath(__file__))))
|
||||||
from modules import *
|
from modules import *
|
||||||
|
|
||||||
def test_push(heap, val, flag=1):
|
|
||||||
|
def test_push(heap: List, val: int, flag: int = 1) -> None:
|
||||||
heapq.heappush(heap, flag * val) # 元素入堆
|
heapq.heappush(heap, flag * val) # 元素入堆
|
||||||
print(f"\n元素 {val} 入堆后")
|
print(f"\n元素 {val} 入堆后")
|
||||||
print_heap([flag * val for val in heap])
|
print_heap([flag * val for val in heap])
|
||||||
|
|
||||||
def test_pop(heap, flag=1):
|
def test_pop(heap: List, flag: int = 1) -> None:
|
||||||
val = flag * heapq.heappop(heap) # 堆顶元素出堆
|
val = flag * heapq.heappop(heap) # 堆顶元素出堆
|
||||||
print(f"\n堆顶元素 {val} 出堆后")
|
print(f"\n堆顶元素 {val} 出堆后")
|
||||||
print_heap([flag * val for val in heap])
|
print_heap([flag * val for val in heap])
|
||||||
@ -37,7 +39,7 @@ if __name__ == "__main__":
|
|||||||
test_push(max_heap, 4, flag)
|
test_push(max_heap, 4, flag)
|
||||||
|
|
||||||
""" 获取堆顶元素 """
|
""" 获取堆顶元素 """
|
||||||
peek = flag * max_heap[0]
|
peek: int = flag * max_heap[0]
|
||||||
print(f"\n堆顶元素为 {peek}")
|
print(f"\n堆顶元素为 {peek}")
|
||||||
|
|
||||||
""" 堆顶元素出堆 """
|
""" 堆顶元素出堆 """
|
||||||
@ -48,16 +50,16 @@ if __name__ == "__main__":
|
|||||||
test_pop(max_heap, flag)
|
test_pop(max_heap, flag)
|
||||||
|
|
||||||
""" 获取堆大小 """
|
""" 获取堆大小 """
|
||||||
size = len(max_heap)
|
size: int = len(max_heap)
|
||||||
print(f"\n堆元素数量为 {size}")
|
print(f"\n堆元素数量为 {size}")
|
||||||
|
|
||||||
""" 判断堆是否为空 """
|
""" 判断堆是否为空 """
|
||||||
is_empty = not max_heap
|
is_empty: bool = not max_heap
|
||||||
print(f"\n堆是否为空 {is_empty}")
|
print(f"\n堆是否为空 {is_empty}")
|
||||||
|
|
||||||
""" 输入列表并建堆 """
|
""" 输入列表并建堆 """
|
||||||
# 时间复杂度为 O(n) ,而非 O(nlogn)
|
# 时间复杂度为 O(n) ,而非 O(nlogn)
|
||||||
min_heap = [1, 3, 2, 5, 4]
|
min_heap: List[int] = [1, 3, 2, 5, 4]
|
||||||
heapq.heapify(min_heap)
|
heapq.heapify(min_heap)
|
||||||
print("\n输入列表并建立小顶堆后")
|
print("\n输入列表并建立小顶堆后")
|
||||||
print_heap(min_heap)
|
print_heap(min_heap)
|
||||||
|
@ -8,7 +8,7 @@ import sys, os.path as osp
|
|||||||
sys.path.append(osp.dirname(osp.dirname(osp.abspath(__file__))))
|
sys.path.append(osp.dirname(osp.dirname(osp.abspath(__file__))))
|
||||||
from modules import *
|
from modules import *
|
||||||
|
|
||||||
def binary_search(nums, target):
|
def binary_search(nums: List[int], target: int) -> int:
|
||||||
""" 二分查找(双闭区间) """
|
""" 二分查找(双闭区间) """
|
||||||
# 初始化双闭区间 [0, n-1] ,即 i, j 分别指向数组首元素、尾元素
|
# 初始化双闭区间 [0, n-1] ,即 i, j 分别指向数组首元素、尾元素
|
||||||
i, j = 0, len(nums) - 1
|
i, j = 0, len(nums) - 1
|
||||||
@ -23,7 +23,7 @@ def binary_search(nums, target):
|
|||||||
return -1 # 未找到目标元素,返回 -1
|
return -1 # 未找到目标元素,返回 -1
|
||||||
|
|
||||||
|
|
||||||
def binary_search1(nums, target):
|
def binary_search1(nums: List[int], target: int) -> int:
|
||||||
""" 二分查找(左闭右开) """
|
""" 二分查找(左闭右开) """
|
||||||
# 初始化左闭右开 [0, n) ,即 i, j 分别指向数组首元素、尾元素+1
|
# 初始化左闭右开 [0, n) ,即 i, j 分别指向数组首元素、尾元素+1
|
||||||
i, j = 0, len(nums)
|
i, j = 0, len(nums)
|
||||||
@ -41,13 +41,13 @@ def binary_search1(nums, target):
|
|||||||
|
|
||||||
""" Driver Code """
|
""" Driver Code """
|
||||||
if __name__ == '__main__':
|
if __name__ == '__main__':
|
||||||
target = 6
|
target: int = 6
|
||||||
nums = [1, 3, 6, 8, 12, 15, 23, 67, 70, 92]
|
nums: List[int] = [1, 3, 6, 8, 12, 15, 23, 67, 70, 92]
|
||||||
|
|
||||||
# 二分查找(双闭区间)
|
# 二分查找(双闭区间)
|
||||||
index = binary_search(nums, target)
|
index: int = binary_search(nums, target)
|
||||||
print("目标元素 6 的索引 = ", index)
|
print("目标元素 6 的索引 = ", index)
|
||||||
|
|
||||||
# 二分查找(左闭右开)
|
# 二分查找(左闭右开)
|
||||||
index = binary_search1(nums, target)
|
index: int = binary_search1(nums, target)
|
||||||
print("目标元素 6 的索引 = ", index)
|
print("目标元素 6 的索引 = ", index)
|
||||||
|
@ -8,38 +8,38 @@ import sys, os.path as osp
|
|||||||
sys.path.append(osp.dirname(osp.dirname(osp.abspath(__file__))))
|
sys.path.append(osp.dirname(osp.dirname(osp.abspath(__file__))))
|
||||||
from modules import *
|
from modules import *
|
||||||
|
|
||||||
def hashing_search_array(mapp, target):
|
def hashing_search_array(mapp: Dict[int, int], target: int) -> int:
|
||||||
""" 哈希查找(数组) """
|
""" 哈希查找(数组) """
|
||||||
# 哈希表的 key: 目标元素,value: 索引
|
# 哈希表的 key: 目标元素,value: 索引
|
||||||
# 若哈希表中无此 key ,返回 -1
|
# 若哈希表中无此 key ,返回 -1
|
||||||
return mapp.get(target, -1)
|
return mapp.get(target, -1)
|
||||||
|
|
||||||
def hashing_search_linkedlist(mapp, target):
|
def hashing_search_linkedlist(mapp: Dict[int, ListNode], target: int) -> Optional[ListNode]:
|
||||||
""" 哈希查找(链表) """
|
""" 哈希查找(链表) """
|
||||||
# 哈希表的 key: 目标元素,value: 结点对象
|
# 哈希表的 key: 目标元素,value: 结点对象
|
||||||
# 若哈希表中无此 key ,返回 -1
|
# 若哈希表中无此 key ,返回 None
|
||||||
return mapp.get(target, -1)
|
return mapp.get(target, None)
|
||||||
|
|
||||||
|
|
||||||
""" Driver Code """
|
""" Driver Code """
|
||||||
if __name__ == '__main__':
|
if __name__ == '__main__':
|
||||||
target = 3
|
target: int = 3
|
||||||
|
|
||||||
# 哈希查找(数组)
|
# 哈希查找(数组)
|
||||||
nums = [1, 5, 3, 2, 4, 7, 5, 9, 10, 8]
|
nums: List[int] = [1, 5, 3, 2, 4, 7, 5, 9, 10, 8]
|
||||||
# 初始化哈希表
|
# 初始化哈希表
|
||||||
mapp = {}
|
mapp: Dict[int, int] = {}
|
||||||
for i in range(len(nums)):
|
for i in range(len(nums)):
|
||||||
mapp[nums[i]] = i # key: 元素,value: 索引
|
mapp[nums[i]] = i # key: 元素,value: 索引
|
||||||
index = hashing_search_array(mapp, target)
|
index: int = hashing_search_array(mapp, target)
|
||||||
print("目标元素 3 的索引 =", index)
|
print("目标元素 3 的索引 =", index)
|
||||||
|
|
||||||
# 哈希查找(链表)
|
# 哈希查找(链表)
|
||||||
head = list_to_linked_list(nums)
|
head: ListNode = list_to_linked_list(nums)
|
||||||
# 初始化哈希表
|
# 初始化哈希表
|
||||||
map1 = {}
|
map1: Dict[int, ListNode] = {}
|
||||||
while head:
|
while head:
|
||||||
map1[head.val] = head # key: 结点值,value: 结点
|
map1[head.val] = head # key: 结点值,value: 结点
|
||||||
head = head.next
|
head = head.next
|
||||||
node = hashing_search_linkedlist(map1, target)
|
node: ListNode = hashing_search_linkedlist(map1, target)
|
||||||
print("目标结点值 3 的对应结点对象为", node)
|
print("目标结点值 3 的对应结点对象为", node)
|
||||||
|
@ -8,7 +8,7 @@ import sys, os.path as osp
|
|||||||
sys.path.append(osp.dirname(osp.dirname(osp.abspath(__file__))))
|
sys.path.append(osp.dirname(osp.dirname(osp.abspath(__file__))))
|
||||||
from modules import *
|
from modules import *
|
||||||
|
|
||||||
def linear_search_array(nums, target):
|
def linear_search_array(nums: List[int], target: int) -> int:
|
||||||
""" 线性查找(数组) """
|
""" 线性查找(数组) """
|
||||||
# 遍历数组
|
# 遍历数组
|
||||||
for i in range(len(nums)):
|
for i in range(len(nums)):
|
||||||
@ -16,7 +16,7 @@ def linear_search_array(nums, target):
|
|||||||
return i
|
return i
|
||||||
return -1 # 未找到目标元素,返回 -1
|
return -1 # 未找到目标元素,返回 -1
|
||||||
|
|
||||||
def linear_search_linkedlist(head, target):
|
def linear_search_linkedlist(head: ListNode, target: int) -> Optional[ListNode]:
|
||||||
""" 线性查找(链表) """
|
""" 线性查找(链表) """
|
||||||
# 遍历链表
|
# 遍历链表
|
||||||
while head:
|
while head:
|
||||||
@ -28,14 +28,14 @@ def linear_search_linkedlist(head, target):
|
|||||||
|
|
||||||
""" Driver Code """
|
""" Driver Code """
|
||||||
if __name__ == '__main__':
|
if __name__ == '__main__':
|
||||||
target = 3
|
target: int = 3
|
||||||
|
|
||||||
# 在数组中执行线性查找
|
# 在数组中执行线性查找
|
||||||
nums = [1, 5, 3, 2, 4, 7, 5, 9, 10, 8]
|
nums: List[int] = [1, 5, 3, 2, 4, 7, 5, 9, 10, 8]
|
||||||
index = linear_search_array(nums, target)
|
index: int = linear_search_array(nums, target)
|
||||||
print("目标元素 3 的索引 =", index)
|
print("目标元素 3 的索引 =", index)
|
||||||
|
|
||||||
# 在链表中执行线性查找
|
# 在链表中执行线性查找
|
||||||
head = list_to_linked_list(nums)
|
head: ListNode = list_to_linked_list(nums)
|
||||||
node = linear_search_linkedlist(head, target)
|
node: Optional[ListNode] = linear_search_linkedlist(head, target)
|
||||||
print("目标结点值 3 的对应结点对象为", node)
|
print("目标结点值 3 的对应结点对象为", node)
|
||||||
|
@ -8,9 +8,9 @@ import sys, os.path as osp
|
|||||||
sys.path.append(osp.dirname(osp.dirname(osp.abspath(__file__))))
|
sys.path.append(osp.dirname(osp.dirname(osp.abspath(__file__))))
|
||||||
from modules import *
|
from modules import *
|
||||||
|
|
||||||
def bubble_sort(nums):
|
def bubble_sort(nums: List[int]) -> None:
|
||||||
""" 冒泡排序 """
|
""" 冒泡排序 """
|
||||||
n = len(nums)
|
n: int = len(nums)
|
||||||
# 外循环:待排序元素数量为 n-1, n-2, ..., 1
|
# 外循环:待排序元素数量为 n-1, n-2, ..., 1
|
||||||
for i in range(n - 1, 0, -1):
|
for i in range(n - 1, 0, -1):
|
||||||
# 内循环:冒泡操作
|
# 内循环:冒泡操作
|
||||||
@ -19,12 +19,12 @@ def bubble_sort(nums):
|
|||||||
# 交换 nums[j] 与 nums[j + 1]
|
# 交换 nums[j] 与 nums[j + 1]
|
||||||
nums[j], nums[j + 1] = nums[j + 1], nums[j]
|
nums[j], nums[j + 1] = nums[j + 1], nums[j]
|
||||||
|
|
||||||
def bubble_sort_with_flag(nums):
|
def bubble_sort_with_flag(nums: List[int]) -> None:
|
||||||
""" 冒泡排序(标志优化) """
|
""" 冒泡排序(标志优化) """
|
||||||
n = len(nums)
|
n: int = len(nums)
|
||||||
# 外循环:待排序元素数量为 n-1, n-2, ..., 1
|
# 外循环:待排序元素数量为 n-1, n-2, ..., 1
|
||||||
for i in range(n - 1, 0, -1):
|
for i in range(n - 1, 0, -1):
|
||||||
flag = False # 初始化标志位
|
flag: bool = False # 初始化标志位
|
||||||
# 内循环:冒泡操作
|
# 内循环:冒泡操作
|
||||||
for j in range(i):
|
for j in range(i):
|
||||||
if nums[j] > nums[j + 1]:
|
if nums[j] > nums[j + 1]:
|
||||||
@ -37,10 +37,10 @@ def bubble_sort_with_flag(nums):
|
|||||||
|
|
||||||
""" Driver Code """
|
""" Driver Code """
|
||||||
if __name__ == '__main__':
|
if __name__ == '__main__':
|
||||||
nums = [4, 1, 3, 1, 5, 2]
|
nums: List[int] = [4, 1, 3, 1, 5, 2]
|
||||||
bubble_sort(nums)
|
bubble_sort(nums)
|
||||||
print("排序后数组 nums =", nums)
|
print("排序后数组 nums =", nums)
|
||||||
|
|
||||||
nums1 = [4, 1, 3, 1, 5, 2]
|
nums1: List[int] = [4, 1, 3, 1, 5, 2]
|
||||||
bubble_sort_with_flag(nums1)
|
bubble_sort_with_flag(nums1)
|
||||||
print("排序后数组 nums =", nums1)
|
print("排序后数组 nums =", nums1)
|
||||||
|
@ -8,12 +8,12 @@ import sys, os.path as osp
|
|||||||
sys.path.append(osp.dirname(osp.dirname(osp.abspath(__file__))))
|
sys.path.append(osp.dirname(osp.dirname(osp.abspath(__file__))))
|
||||||
from modules import *
|
from modules import *
|
||||||
|
|
||||||
def insertion_sort(nums):
|
def insertion_sort(nums: List[int]) -> None:
|
||||||
""" 插入排序 """
|
""" 插入排序 """
|
||||||
# 外循环:base = nums[1], nums[2], ..., nums[n-1]
|
# 外循环:base = nums[1], nums[2], ..., nums[n-1]
|
||||||
for i in range(1, len(nums)):
|
for i in range(1, len(nums)):
|
||||||
base = nums[i]
|
base: int = nums[i]
|
||||||
j = i - 1
|
j: int = i - 1
|
||||||
# 内循环:将 base 插入到左边的正确位置
|
# 内循环:将 base 插入到左边的正确位置
|
||||||
while j >= 0 and nums[j] > base:
|
while j >= 0 and nums[j] > base:
|
||||||
nums[j + 1] = nums[j] # 1. 将 nums[j] 向右移动一位
|
nums[j + 1] = nums[j] # 1. 将 nums[j] 向右移动一位
|
||||||
@ -23,6 +23,6 @@ def insertion_sort(nums):
|
|||||||
|
|
||||||
""" Driver Code """
|
""" Driver Code """
|
||||||
if __name__ == '__main__':
|
if __name__ == '__main__':
|
||||||
nums = [4, 1, 3, 1, 5, 2]
|
nums: List[int] = [4, 1, 3, 1, 5, 2]
|
||||||
insertion_sort(nums)
|
insertion_sort(nums)
|
||||||
print("排序后数组 nums =", nums)
|
print("排序后数组 nums =", nums)
|
||||||
|
@ -8,18 +8,21 @@ import sys, os.path as osp
|
|||||||
sys.path.append(osp.dirname(osp.dirname(osp.abspath(__file__))))
|
sys.path.append(osp.dirname(osp.dirname(osp.abspath(__file__))))
|
||||||
from modules import *
|
from modules import *
|
||||||
|
|
||||||
def merge(nums, left, mid, right):
|
def merge(nums: List[int], left: int, mid: int, right: int) -> None:
|
||||||
""" 合并左子数组和右子数组 """
|
""" 合并左子数组和右子数组 """
|
||||||
# 左子数组区间 [left, mid]
|
# 左子数组区间 [left, mid]
|
||||||
# 右子数组区间 [mid + 1, right]
|
# 右子数组区间 [mid + 1, right]
|
||||||
# 初始化辅助数组 借助 copy模块
|
# 初始化辅助数组 借助 copy模块
|
||||||
tmp = nums[left:right + 1]
|
tmp: List[int] = nums[left:right + 1].copy()
|
||||||
# 左子数组的起始索引和结束索引
|
# 左子数组的起始索引和结束索引
|
||||||
left_start, left_end = left - left, mid - left
|
left_start: int = 0
|
||||||
|
left_end: int = mid - left
|
||||||
# 右子数组的起始索引和结束索引
|
# 右子数组的起始索引和结束索引
|
||||||
right_start, right_end = mid + 1 - left, right - left
|
right_start: int = mid + 1 - left
|
||||||
|
right_end: int = right - left
|
||||||
# i, j 分别指向左子数组、右子数组的首元素
|
# i, j 分别指向左子数组、右子数组的首元素
|
||||||
i, j = left_start, right_start
|
i: int = left_start
|
||||||
|
j: int = right_start
|
||||||
# 通过覆盖原数组 nums 来合并左子数组和右子数组
|
# 通过覆盖原数组 nums 来合并左子数组和右子数组
|
||||||
for k in range(left, right + 1):
|
for k in range(left, right + 1):
|
||||||
# 若“左子数组已全部合并完”,则选取右子数组元素,并且 j++
|
# 若“左子数组已全部合并完”,则选取右子数组元素,并且 j++
|
||||||
@ -35,13 +38,13 @@ def merge(nums, left, mid, right):
|
|||||||
nums[k] = tmp[j]
|
nums[k] = tmp[j]
|
||||||
j += 1
|
j += 1
|
||||||
|
|
||||||
def merge_sort(nums, left, right):
|
def merge_sort(nums: List[int], left: int, right: int) -> None:
|
||||||
""" 归并排序 """
|
""" 归并排序 """
|
||||||
# 终止条件
|
# 终止条件
|
||||||
if left >= right:
|
if left >= right:
|
||||||
return # 当子数组长度为 1 时终止递归
|
return # 当子数组长度为 1 时终止递归
|
||||||
# 划分阶段
|
# 划分阶段
|
||||||
mid = (left + right) // 2 # 计算中点
|
mid: int = (left + right) // 2 # 计算中点
|
||||||
merge_sort(nums, left, mid) # 递归左子数组
|
merge_sort(nums, left, mid) # 递归左子数组
|
||||||
merge_sort(nums, mid + 1, right) # 递归右子数组
|
merge_sort(nums, mid + 1, right) # 递归右子数组
|
||||||
# 合并阶段
|
# 合并阶段
|
||||||
@ -50,6 +53,6 @@ def merge_sort(nums, left, right):
|
|||||||
|
|
||||||
""" Driver Code """
|
""" Driver Code """
|
||||||
if __name__ == '__main__':
|
if __name__ == '__main__':
|
||||||
nums = [ 7, 3, 2, 6, 0, 1, 5, 4 ]
|
nums: List[int] = [ 7, 3, 2, 6, 0, 1, 5, 4 ]
|
||||||
merge_sort(nums, 0, len(nums) - 1)
|
merge_sort(nums, 0, len(nums) - 1)
|
||||||
print("归并排序完成后 nums =", nums)
|
print("归并排序完成后 nums =", nums)
|
||||||
|
@ -10,7 +10,7 @@ from modules import *
|
|||||||
|
|
||||||
class QuickSort:
|
class QuickSort:
|
||||||
""" 快速排序类 """
|
""" 快速排序类 """
|
||||||
def partition(self, nums, left, right):
|
def partition(self, nums: List[int], left: int, right: int) -> int:
|
||||||
""" 哨兵划分 """
|
""" 哨兵划分 """
|
||||||
# 以 nums[left] 作为基准数
|
# 以 nums[left] 作为基准数
|
||||||
i, j = left, right
|
i, j = left, right
|
||||||
@ -25,20 +25,20 @@ class QuickSort:
|
|||||||
nums[i], nums[left] = nums[left], nums[i]
|
nums[i], nums[left] = nums[left], nums[i]
|
||||||
return i # 返回基准数的索引
|
return i # 返回基准数的索引
|
||||||
|
|
||||||
def quick_sort(self, nums, left, right):
|
def quick_sort(self, nums: List[int], left: int, right: int) -> None:
|
||||||
""" 快速排序 """
|
""" 快速排序 """
|
||||||
# 子数组长度为 1 时终止递归
|
# 子数组长度为 1 时终止递归
|
||||||
if left >= right:
|
if left >= right:
|
||||||
return
|
return
|
||||||
# 哨兵划分
|
# 哨兵划分
|
||||||
pivot = self.partition(nums, left, right)
|
pivot: int = self.partition(nums, left, right)
|
||||||
# 递归左子数组、右子数组
|
# 递归左子数组、右子数组
|
||||||
self.quick_sort(nums, left, pivot - 1)
|
self.quick_sort(nums, left, pivot - 1)
|
||||||
self.quick_sort(nums, pivot + 1, right)
|
self.quick_sort(nums, pivot + 1, right)
|
||||||
|
|
||||||
class QuickSortMedian:
|
class QuickSortMedian:
|
||||||
""" 快速排序类(中位基准数优化)"""
|
""" 快速排序类(中位基准数优化)"""
|
||||||
def median_three(self, nums, left, mid, right):
|
def median_three(self, nums: List[int], left: int, mid: int, right: int) -> int:
|
||||||
""" 选取三个元素的中位数 """
|
""" 选取三个元素的中位数 """
|
||||||
# 此处使用异或运算来简化代码
|
# 此处使用异或运算来简化代码
|
||||||
# 异或规则为 0 ^ 0 = 1 ^ 1 = 0, 0 ^ 1 = 1 ^ 0 = 1
|
# 异或规则为 0 ^ 0 = 1 ^ 1 = 0, 0 ^ 1 = 1 ^ 0 = 1
|
||||||
@ -48,10 +48,10 @@ class QuickSortMedian:
|
|||||||
return mid
|
return mid
|
||||||
return right
|
return right
|
||||||
|
|
||||||
def partition(self, nums, left, right):
|
def partition(self, nums: List[int], left: int, right: int) -> int:
|
||||||
""" 哨兵划分(三数取中值) """
|
""" 哨兵划分(三数取中值) """
|
||||||
# 以 nums[left] 作为基准数
|
# 以 nums[left] 作为基准数
|
||||||
med = self.median_three(nums, left, (left + right) // 2, right)
|
med: int = self.median_three(nums, left, (left + right) // 2, right)
|
||||||
# 将中位数交换至数组最左端
|
# 将中位数交换至数组最左端
|
||||||
nums[left], nums[med] = nums[med], nums[left]
|
nums[left], nums[med] = nums[med], nums[left]
|
||||||
# 以 nums[left] 作为基准数
|
# 以 nums[left] 作为基准数
|
||||||
@ -67,19 +67,20 @@ class QuickSortMedian:
|
|||||||
nums[i], nums[left] = nums[left], nums[i]
|
nums[i], nums[left] = nums[left], nums[i]
|
||||||
return i # 返回基准数的索引
|
return i # 返回基准数的索引
|
||||||
|
|
||||||
def quick_sort(self, nums, left, right):
|
def quick_sort(self, nums: List[int], left: int, right: int) -> None:
|
||||||
""" 快速排序 """
|
""" 快速排序 """
|
||||||
# 子数组长度为 1 时终止递归
|
# 子数组长度为 1 时终止递归
|
||||||
if left >= right: return
|
if left >= right:
|
||||||
|
return
|
||||||
# 哨兵划分
|
# 哨兵划分
|
||||||
pivot = self.partition(nums, left, right)
|
pivot: int = self.partition(nums, left, right)
|
||||||
# 递归左子数组、右子数组
|
# 递归左子数组、右子数组
|
||||||
self.quick_sort(nums, left, pivot - 1)
|
self.quick_sort(nums, left, pivot - 1)
|
||||||
self.quick_sort(nums, pivot + 1, right)
|
self.quick_sort(nums, pivot + 1, right)
|
||||||
|
|
||||||
class QuickSortTailCall:
|
class QuickSortTailCall:
|
||||||
""" 快速排序类(尾递归优化) """
|
""" 快速排序类(尾递归优化) """
|
||||||
def partition(self, nums, left, right):
|
def partition(self, nums: List[int], left: int, right: int) -> int:
|
||||||
""" 哨兵划分 """
|
""" 哨兵划分 """
|
||||||
# 以 nums[left] 作为基准数
|
# 以 nums[left] 作为基准数
|
||||||
i, j = left, right
|
i, j = left, right
|
||||||
@ -94,12 +95,12 @@ class QuickSortTailCall:
|
|||||||
nums[i], nums[left] = nums[left], nums[i]
|
nums[i], nums[left] = nums[left], nums[i]
|
||||||
return i # 返回基准数的索引
|
return i # 返回基准数的索引
|
||||||
|
|
||||||
def quick_sort(self, nums, left, right):
|
def quick_sort(self, nums: List[int], left: int, right: int) -> None:
|
||||||
""" 快速排序(尾递归优化) """
|
""" 快速排序(尾递归优化) """
|
||||||
# 子数组长度为 1 时终止
|
# 子数组长度为 1 时终止
|
||||||
while left < right:
|
while left < right:
|
||||||
# 哨兵划分操作
|
# 哨兵划分操作
|
||||||
pivot = self.partition(nums, left, right)
|
pivot: int = self.partition(nums, left, right)
|
||||||
# 对两个子数组中较短的那个执行快排
|
# 对两个子数组中较短的那个执行快排
|
||||||
if pivot - left < right - pivot:
|
if pivot - left < right - pivot:
|
||||||
self.quick_sort(nums, left, pivot - 1) # 递归排序左子数组
|
self.quick_sort(nums, left, pivot - 1) # 递归排序左子数组
|
||||||
@ -112,16 +113,16 @@ class QuickSortTailCall:
|
|||||||
""" Driver Code """
|
""" Driver Code """
|
||||||
if __name__ == '__main__':
|
if __name__ == '__main__':
|
||||||
# 快速排序
|
# 快速排序
|
||||||
nums = [2, 4, 1, 0, 3, 5]
|
nums: List[int] = [2, 4, 1, 0, 3, 5]
|
||||||
QuickSort().quick_sort(nums, 0, len(nums) - 1)
|
QuickSort().quick_sort(nums, 0, len(nums) - 1)
|
||||||
print("快速排序完成后 nums =", nums)
|
print("快速排序完成后 nums =", nums)
|
||||||
|
|
||||||
# 快速排序(中位基准数优化)
|
# 快速排序(中位基准数优化)
|
||||||
nums1 = [2, 4, 1, 0, 3, 5]
|
nums1: List[int] = [2, 4, 1, 0, 3, 5]
|
||||||
QuickSortMedian().quick_sort(nums1, 0, len(nums1) - 1)
|
QuickSortMedian().quick_sort(nums1, 0, len(nums1) - 1)
|
||||||
print("快速排序(中位基准数优化)完成后 nums =", nums1)
|
print("快速排序(中位基准数优化)完成后 nums =", nums1)
|
||||||
|
|
||||||
# 快速排序(尾递归优化)
|
# 快速排序(尾递归优化)
|
||||||
nums2 = [2, 4, 1, 0, 3, 5]
|
nums2: List[int] = [2, 4, 1, 0, 3, 5]
|
||||||
QuickSortTailCall().quick_sort(nums2, 0, len(nums2) - 1)
|
QuickSortTailCall().quick_sort(nums2, 0, len(nums2) - 1)
|
||||||
print("快速排序(尾递归优化)完成后 nums =", nums2)
|
print("快速排序(尾递归优化)完成后 nums =", nums2)
|
||||||
|
@ -4,94 +4,94 @@ Created Time: 2023-03-01
|
|||||||
Author: Krahets (krahets@163.com)
|
Author: Krahets (krahets@163.com)
|
||||||
"""
|
"""
|
||||||
|
|
||||||
import os.path as osp
|
import sys, os.path as osp
|
||||||
import sys
|
|
||||||
|
|
||||||
sys.path.append(osp.dirname(osp.dirname(osp.abspath(__file__))))
|
sys.path.append(osp.dirname(osp.dirname(osp.abspath(__file__))))
|
||||||
from modules import *
|
from modules import *
|
||||||
|
|
||||||
|
|
||||||
class ArrayDeque:
|
class ArrayDeque:
|
||||||
""" 基于环形数组实现的双向队列 """
|
""" 基于环形数组实现的双向队列 """
|
||||||
def __init__(self, capacity):
|
|
||||||
""" 构造方法 """
|
|
||||||
self.nums = [0] * capacity
|
|
||||||
self.front = 0
|
|
||||||
self.que_size = 0
|
|
||||||
|
|
||||||
def capacity(self):
|
def __init__(self, capacity: int) -> None:
|
||||||
|
""" 构造方法 """
|
||||||
|
self.__nums: List[int] = [0] * capacity
|
||||||
|
self.__front: int = 0
|
||||||
|
self.__size: int = 0
|
||||||
|
|
||||||
|
def capacity(self) -> int:
|
||||||
""" 获取双向队列的容量 """
|
""" 获取双向队列的容量 """
|
||||||
return len(self.nums)
|
return len(self.__nums)
|
||||||
|
|
||||||
def size(self):
|
def size(self) -> int:
|
||||||
""" 获取双向队列的长度 """
|
""" 获取双向队列的长度 """
|
||||||
return self.que_size
|
return self.__size
|
||||||
|
|
||||||
def is_empty(self):
|
def is_empty(self) -> bool:
|
||||||
""" 判断双向队列是否为空 """
|
""" 判断双向队列是否为空 """
|
||||||
return self.que_size == 0
|
return self.__size == 0
|
||||||
|
|
||||||
def index(self, i):
|
def index(self, i: int) -> int:
|
||||||
""" 计算环形数组索引 """
|
""" 计算环形数组索引 """
|
||||||
# 通过取余操作实现数组首尾相连
|
# 通过取余操作实现数组首尾相连
|
||||||
# 当 i 越过数组尾部后,回到头部
|
# 当 i 越过数组尾部后,回到头部
|
||||||
# 当 i 越过数组头部后,回到尾部
|
# 当 i 越过数组头部后,回到尾部
|
||||||
return (i + self.capacity()) % self.capacity()
|
return (i + self.capacity()) % self.capacity()
|
||||||
|
|
||||||
def push_first(self, num):
|
def push_first(self, num: int) -> None:
|
||||||
""" 队首入队 """
|
""" 队首入队 """
|
||||||
if self.que_size == self.capacity():
|
if self.__size == self.capacity():
|
||||||
print("双向队列已满")
|
print("双向队列已满")
|
||||||
return
|
return
|
||||||
# 队首指针向左移动一位
|
# 队首指针向左移动一位
|
||||||
# 通过取余操作,实现 front 越过数组头部后回到尾部
|
# 通过取余操作,实现 front 越过数组头部后回到尾部
|
||||||
self.front = self.index(self.front-1)
|
self.__front = self.index(self.__front - 1)
|
||||||
# 将 num 添加至队首
|
# 将 num 添加至队首
|
||||||
self.nums[self.front] = num
|
self.__nums[self.__front] = num
|
||||||
self.que_size += 1
|
self.__size += 1
|
||||||
|
|
||||||
def push_last(self, num):
|
def push_last(self, num: int) -> None:
|
||||||
""" 队尾入队 """
|
""" 队尾入队 """
|
||||||
if self.que_size == self.capacity():
|
if self.__size == self.capacity():
|
||||||
print("双向队列已满")
|
print("双向队列已满")
|
||||||
return
|
return
|
||||||
# 计算尾指针,指向队尾索引 + 1
|
# 计算尾指针,指向队尾索引 + 1
|
||||||
rear = self.index(self.front + self.que_size)
|
rear = self.index(self.__front + self.__size)
|
||||||
# 将 num 添加至队尾
|
# 将 num 添加至队尾
|
||||||
self.nums[rear] = num
|
self.__nums[rear] = num
|
||||||
self.que_size += 1
|
self.__size += 1
|
||||||
|
|
||||||
def poll_first(self):
|
def poll_first(self) -> int:
|
||||||
""" 队首出队 """
|
""" 队首出队 """
|
||||||
num = self.peek_first()
|
num = self.peek_first()
|
||||||
# 队首指针向后移动一位
|
# 队首指针向后移动一位
|
||||||
self.front = self.index(self.front+1)
|
self.__front = self.index(self.__front + 1)
|
||||||
self.que_size -= 1
|
self.__size -= 1
|
||||||
return num
|
return num
|
||||||
|
|
||||||
def poll_last(self):
|
def poll_last(self) -> int:
|
||||||
""" 队尾出队 """
|
""" 队尾出队 """
|
||||||
num = self.peek_last()
|
num = self.peek_last()
|
||||||
self.que_size -= 1
|
self.__size -= 1
|
||||||
return num
|
return num
|
||||||
|
|
||||||
def peek_first(self):
|
def peek_first(self) -> int:
|
||||||
""" 访问队首元素 """
|
""" 访问队首元素 """
|
||||||
assert not self.is_empty(), "双向队列为空"
|
assert not self.is_empty(), "双向队列为空"
|
||||||
return self.nums[self.front]
|
return self.__nums[self.__front]
|
||||||
|
|
||||||
def peek_last(self):
|
def peek_last(self) -> int:
|
||||||
""" 访问队尾元素 """
|
""" 访问队尾元素 """
|
||||||
assert not self.is_empty(), "双向队列为空"
|
assert not self.is_empty(), "双向队列为空"
|
||||||
# 计算尾元素索引
|
# 计算尾元素索引
|
||||||
last = self.index(self.front + self.que_size - 1)
|
last = self.index(self.__front + self.__size - 1)
|
||||||
return self.nums[last]
|
return self.__nums[last]
|
||||||
|
|
||||||
def to_array(self):
|
def to_array(self) -> List[int]:
|
||||||
""" 返回数组用于打印 """
|
""" 返回数组用于打印 """
|
||||||
# 仅转换有效长度范围内的列表元素
|
# 仅转换有效长度范围内的列表元素
|
||||||
res = []
|
res = []
|
||||||
for i in range(self.que_size):
|
for i in range(self.__size):
|
||||||
res.append(self.nums[self.index(self.front+i)])
|
res.append(self.__nums[self.index(self.__front + i)])
|
||||||
return res
|
return res
|
||||||
|
|
||||||
|
|
||||||
@ -105,9 +105,9 @@ if __name__ == "__main__":
|
|||||||
print("双向队列 deque =", deque.to_array())
|
print("双向队列 deque =", deque.to_array())
|
||||||
|
|
||||||
""" 访问元素 """
|
""" 访问元素 """
|
||||||
peek_first = deque.peek_first()
|
peek_first: int = deque.peek_first()
|
||||||
print("队首元素 peek_first =", peek_first)
|
print("队首元素 peek_first =", peek_first)
|
||||||
peek_last = deque.peek_last()
|
peek_last: int = deque.peek_last()
|
||||||
print("队尾元素 peek_last =", peek_last)
|
print("队尾元素 peek_last =", peek_last)
|
||||||
|
|
||||||
""" 元素入队 """
|
""" 元素入队 """
|
||||||
@ -117,15 +117,15 @@ if __name__ == "__main__":
|
|||||||
print("元素 1 队首入队后 deque =", deque.to_array())
|
print("元素 1 队首入队后 deque =", deque.to_array())
|
||||||
|
|
||||||
""" 元素出队 """
|
""" 元素出队 """
|
||||||
poll_last = deque.poll_last()
|
poll_last: int = deque.poll_last()
|
||||||
print("队尾出队元素 =", poll_last, ",队尾出队后 deque =", deque.to_array())
|
print("队尾出队元素 =", poll_last, ",队尾出队后 deque =", deque.to_array())
|
||||||
poll_first = deque.poll_first()
|
poll_first: int = deque.poll_first()
|
||||||
print("队首出队元素 =", poll_first, ",队首出队后 deque =", deque.to_array())
|
print("队首出队元素 =", poll_first, ",队首出队后 deque =", deque.to_array())
|
||||||
|
|
||||||
""" 获取双向队列的长度 """
|
""" 获取双向队列的长度 """
|
||||||
size = deque.size()
|
size: int = deque.size()
|
||||||
print("双向队列长度 size =", size)
|
print("双向队列长度 size =", size)
|
||||||
|
|
||||||
""" 判断双向队列是否为空 """
|
""" 判断双向队列是否为空 """
|
||||||
is_empty = deque.is_empty()
|
is_empty: bool = deque.is_empty()
|
||||||
print("双向队列是否为空 =", is_empty)
|
print("双向队列是否为空 =", is_empty)
|
||||||
|
@ -4,59 +4,57 @@ Created Time: 2022-12-01
|
|||||||
Author: Peng Chen (pengchzn@gmail.com)
|
Author: Peng Chen (pengchzn@gmail.com)
|
||||||
"""
|
"""
|
||||||
|
|
||||||
import os.path as osp
|
import sys, os.path as osp
|
||||||
import sys
|
|
||||||
|
|
||||||
sys.path.append(osp.dirname(osp.dirname(osp.abspath(__file__))))
|
sys.path.append(osp.dirname(osp.dirname(osp.abspath(__file__))))
|
||||||
from modules import *
|
from modules import *
|
||||||
|
|
||||||
class ArrayQueue:
|
class ArrayQueue:
|
||||||
""" 基于环形数组实现的队列 """
|
""" 基于环形数组实现的队列 """
|
||||||
def __init__(self, size):
|
def __init__(self, size: int) -> None:
|
||||||
""" 构造方法 """
|
""" 构造方法 """
|
||||||
self.__nums = [0] * size # 用于存储队列元素的数组
|
self.__nums: List[int] = [0] * size # 用于存储队列元素的数组
|
||||||
self.__front = 0 # 队首指针,指向队首元素
|
self.__front: int = 0 # 队首指针,指向队首元素
|
||||||
self.__size = 0 # 队列长度
|
self.__size: int = 0 # 队列长度
|
||||||
|
|
||||||
def capacity(self):
|
def capacity(self) -> int:
|
||||||
""" 获取队列的容量 """
|
""" 获取队列的容量 """
|
||||||
return len(self.__nums)
|
return len(self.__nums)
|
||||||
|
|
||||||
def size(self):
|
def size(self) -> int:
|
||||||
""" 获取队列的长度 """
|
""" 获取队列的长度 """
|
||||||
return self.__size
|
return self.__size
|
||||||
|
|
||||||
def is_empty(self):
|
def is_empty(self) -> bool:
|
||||||
""" 判断队列是否为空 """
|
""" 判断队列是否为空 """
|
||||||
return self.__size == 0
|
return self.__size == 0
|
||||||
|
|
||||||
def push(self, num):
|
def push(self, num: int) -> None:
|
||||||
""" 入队 """
|
""" 入队 """
|
||||||
assert self.__size < self.capacity(), "队列已满"
|
assert self.__size < self.capacity(), "队列已满"
|
||||||
# 计算尾指针,指向队尾索引 + 1
|
# 计算尾指针,指向队尾索引 + 1
|
||||||
# 通过取余操作,实现 rear 越过数组尾部后回到头部
|
# 通过取余操作,实现 rear 越过数组尾部后回到头部
|
||||||
rear = (self.__front + self.__size) % self.capacity()
|
rear: int = (self.__front + self.__size) % self.capacity()
|
||||||
# 将 num 添加至队尾
|
# 将 num 添加至队尾
|
||||||
self.__nums[rear] = num
|
self.__nums[rear] = num
|
||||||
self.__size += 1
|
self.__size += 1
|
||||||
|
|
||||||
def poll(self):
|
def poll(self) -> int:
|
||||||
""" 出队 """
|
""" 出队 """
|
||||||
num = self.peek()
|
num: int = self.peek()
|
||||||
# 队首指针向后移动一位,若越过尾部则返回到数组头部
|
# 队首指针向后移动一位,若越过尾部则返回到数组头部
|
||||||
self.__front = (self.__front + 1) % self.capacity()
|
self.__front = (self.__front + 1) % self.capacity()
|
||||||
self.__size -= 1
|
self.__size -= 1
|
||||||
return num
|
return num
|
||||||
|
|
||||||
def peek(self):
|
def peek(self) -> int:
|
||||||
""" 访问队首元素 """
|
""" 访问队首元素 """
|
||||||
assert not self.is_empty(), "队列为空"
|
assert not self.is_empty(), "队列为空"
|
||||||
return self.__nums[self.__front]
|
return self.__nums[self.__front]
|
||||||
|
|
||||||
def to_list(self):
|
def to_list(self) -> List[int]:
|
||||||
""" 返回列表用于打印 """
|
""" 返回列表用于打印 """
|
||||||
res = [0] * self.size()
|
res: List[int] = [0] * self.size()
|
||||||
j = self.__front
|
j: int = self.__front
|
||||||
for i in range(self.size()):
|
for i in range(self.size()):
|
||||||
res[i] = self.__nums[(j % self.capacity())]
|
res[i] = self.__nums[(j % self.capacity())]
|
||||||
j += 1
|
j += 1
|
||||||
@ -77,24 +75,24 @@ if __name__ == "__main__":
|
|||||||
print("队列 queue =", queue.to_list())
|
print("队列 queue =", queue.to_list())
|
||||||
|
|
||||||
""" 访问队首元素 """
|
""" 访问队首元素 """
|
||||||
peek = queue.peek()
|
peek: int = queue.peek()
|
||||||
print("队首元素 peek =", peek)
|
print("队首元素 peek =", peek)
|
||||||
|
|
||||||
""" 元素出队 """
|
""" 元素出队 """
|
||||||
poll = queue.poll()
|
poll: int = queue.poll()
|
||||||
print("出队元素 poll =", poll)
|
print("出队元素 poll =", poll)
|
||||||
print("出队后 queue =", queue.to_list())
|
print("出队后 queue =", queue.to_list())
|
||||||
|
|
||||||
""" 获取队列的长度 """
|
""" 获取队列的长度 """
|
||||||
size = queue.size()
|
size: int = queue.size()
|
||||||
print("队列长度 size =", size)
|
print("队列长度 size =", size)
|
||||||
|
|
||||||
""" 判断队列是否为空 """
|
""" 判断队列是否为空 """
|
||||||
is_empty = queue.is_empty()
|
is_empty: bool = queue.is_empty()
|
||||||
print("队列是否为空 =", is_empty)
|
print("队列是否为空 =", is_empty)
|
||||||
|
|
||||||
""" 测试环形数组 """
|
""" 测试环形数组 """
|
||||||
for i in range(10):
|
for i in range(10):
|
||||||
queue.push(i);
|
queue.push(i)
|
||||||
queue.poll();
|
queue.poll()
|
||||||
print("第", i, "轮入队 + 出队后 queue = ", queue.to_list());
|
print("第", i, "轮入队 + 出队后 queue = ", queue.to_list())
|
||||||
|
@ -10,33 +10,33 @@ from modules import *
|
|||||||
|
|
||||||
class ArrayStack:
|
class ArrayStack:
|
||||||
""" 基于数组实现的栈 """
|
""" 基于数组实现的栈 """
|
||||||
def __init__(self):
|
def __init__(self) -> None:
|
||||||
""" 构造方法 """
|
""" 构造方法 """
|
||||||
self.__stack = []
|
self.__stack: List[int] = []
|
||||||
|
|
||||||
def size(self):
|
def size(self) -> int:
|
||||||
""" 获取栈的长度 """
|
""" 获取栈的长度 """
|
||||||
return len(self.__stack)
|
return len(self.__stack)
|
||||||
|
|
||||||
def is_empty(self):
|
def is_empty(self) -> bool:
|
||||||
""" 判断栈是否为空 """
|
""" 判断栈是否为空 """
|
||||||
return self.__stack == []
|
return self.__stack == []
|
||||||
|
|
||||||
def push(self, item):
|
def push(self, item: int) -> None:
|
||||||
""" 入栈 """
|
""" 入栈 """
|
||||||
self.__stack.append(item)
|
self.__stack.append(item)
|
||||||
|
|
||||||
def pop(self):
|
def pop(self) -> int:
|
||||||
""" 出栈 """
|
""" 出栈 """
|
||||||
assert not self.is_empty(), "栈为空"
|
assert not self.is_empty(), "栈为空"
|
||||||
return self.__stack.pop()
|
return self.__stack.pop()
|
||||||
|
|
||||||
def peek(self):
|
def peek(self) -> int:
|
||||||
""" 访问栈顶元素 """
|
""" 访问栈顶元素 """
|
||||||
assert not self.is_empty(), "栈为空"
|
assert not self.is_empty(), "栈为空"
|
||||||
return self.__stack[-1]
|
return self.__stack[-1]
|
||||||
|
|
||||||
def to_list(self):
|
def to_list(self) -> List[int]:
|
||||||
""" 返回列表用于打印 """
|
""" 返回列表用于打印 """
|
||||||
return self.__stack
|
return self.__stack
|
||||||
|
|
||||||
@ -55,18 +55,18 @@ if __name__ == "__main__":
|
|||||||
print("栈 stack =", stack.to_list())
|
print("栈 stack =", stack.to_list())
|
||||||
|
|
||||||
""" 访问栈顶元素 """
|
""" 访问栈顶元素 """
|
||||||
peek = stack.peek()
|
peek: int = stack.peek()
|
||||||
print("栈顶元素 peek =", peek)
|
print("栈顶元素 peek =", peek)
|
||||||
|
|
||||||
""" 元素出栈 """
|
""" 元素出栈 """
|
||||||
pop = stack.pop()
|
pop: int = stack.pop()
|
||||||
print("出栈元素 pop =", pop)
|
print("出栈元素 pop =", pop)
|
||||||
print("出栈后 stack =", stack.to_list())
|
print("出栈后 stack =", stack.to_list())
|
||||||
|
|
||||||
""" 获取栈的长度 """
|
""" 获取栈的长度 """
|
||||||
size = stack.size()
|
size: int = stack.size()
|
||||||
print("栈的长度 size =", size)
|
print("栈的长度 size =", size)
|
||||||
|
|
||||||
""" 判断是否为空 """
|
""" 判断是否为空 """
|
||||||
is_empty = stack.is_empty()
|
is_empty: bool = stack.is_empty()
|
||||||
print("栈是否为空 =", is_empty)
|
print("栈是否为空 =", is_empty)
|
||||||
|
@ -4,19 +4,15 @@ Created Time: 2022-11-29
|
|||||||
Author: Peng Chen (pengchzn@gmail.com)
|
Author: Peng Chen (pengchzn@gmail.com)
|
||||||
"""
|
"""
|
||||||
|
|
||||||
import os.path as osp
|
import sys, os.path as osp
|
||||||
import sys
|
|
||||||
|
|
||||||
sys.path.append(osp.dirname(osp.dirname(osp.abspath(__file__))))
|
sys.path.append(osp.dirname(osp.dirname(osp.abspath(__file__))))
|
||||||
from modules import *
|
from modules import *
|
||||||
|
|
||||||
from collections import deque
|
|
||||||
|
|
||||||
|
|
||||||
""" Driver Code """
|
""" Driver Code """
|
||||||
if __name__ == "__main__":
|
if __name__ == "__main__":
|
||||||
""" 初始化双向队列 """
|
""" 初始化双向队列 """
|
||||||
deque = deque()
|
deque: Deque[int] = collections.deque()
|
||||||
|
|
||||||
""" 元素入队 """
|
""" 元素入队 """
|
||||||
deque.append(2) # 添加至队尾
|
deque.append(2) # 添加至队尾
|
||||||
@ -27,23 +23,23 @@ if __name__ == "__main__":
|
|||||||
print("双向队列 deque =", deque)
|
print("双向队列 deque =", deque)
|
||||||
|
|
||||||
""" 访问元素 """
|
""" 访问元素 """
|
||||||
front = deque[0] # 队首元素
|
front: int = deque[0] # 队首元素
|
||||||
print("队首元素 front =", front)
|
print("队首元素 front =", front)
|
||||||
rear = deque[-1] # 队尾元素
|
rear: int = deque[-1] # 队尾元素
|
||||||
print("队尾元素 rear =", rear)
|
print("队尾元素 rear =", rear)
|
||||||
|
|
||||||
""" 元素出队 """
|
""" 元素出队 """
|
||||||
pop_front = deque.popleft() # 队首元素出队
|
pop_front: int = deque.popleft() # 队首元素出队
|
||||||
print("队首出队元素 pop_front =", pop_front)
|
print("队首出队元素 pop_front =", pop_front)
|
||||||
print("队首出队后 deque =", deque)
|
print("队首出队后 deque =", deque)
|
||||||
pop_rear = deque.pop() # 队尾元素出队
|
pop_rear: int = deque.pop() # 队尾元素出队
|
||||||
print("队尾出队元素 pop_rear =", pop_rear)
|
print("队尾出队元素 pop_rear =", pop_rear)
|
||||||
print("队尾出队后 deque =", deque)
|
print("队尾出队后 deque =", deque)
|
||||||
|
|
||||||
""" 获取双向队列的长度 """
|
""" 获取双向队列的长度 """
|
||||||
size = len(deque)
|
size: int = len(deque)
|
||||||
print("双向队列长度 size =", size)
|
print("双向队列长度 size =", size)
|
||||||
|
|
||||||
""" 判断双向队列是否为空 """
|
""" 判断双向队列是否为空 """
|
||||||
is_empty = len(deque) == 0
|
is_empty: bool = len(deque) == 0
|
||||||
print("双向队列是否为空 =", is_empty)
|
print("双向队列是否为空 =", is_empty)
|
||||||
|
@ -4,36 +4,35 @@ Created Time: 2023-03-01
|
|||||||
Author: Krahets (krahets@163.com)
|
Author: Krahets (krahets@163.com)
|
||||||
"""
|
"""
|
||||||
|
|
||||||
import os.path as osp
|
import sys, os.path as osp
|
||||||
import sys
|
|
||||||
|
|
||||||
sys.path.append(osp.dirname(osp.dirname(osp.abspath(__file__))))
|
sys.path.append(osp.dirname(osp.dirname(osp.abspath(__file__))))
|
||||||
from modules import *
|
from modules import *
|
||||||
|
|
||||||
class ListNode:
|
class ListNode:
|
||||||
""" 双向链表结点 """
|
""" 双向链表结点 """
|
||||||
def __init__(self, val):
|
def __init__(self, val: int) -> None:
|
||||||
""" 构造方法 """
|
""" 构造方法 """
|
||||||
self.val = val
|
self.val: int = val
|
||||||
self.next = None # 后继结点引用(指针)
|
self.next: Optional[ListNode] = None # 后继结点引用(指针)
|
||||||
self.prev = None # 前驱结点引用(指针)
|
self.prev: Optional[ListNode] = None # 前驱结点引用(指针)
|
||||||
|
|
||||||
class LinkedListDeque:
|
class LinkedListDeque:
|
||||||
""" 基于双向链表实现的双向队列 """
|
""" 基于双向链表实现的双向队列 """
|
||||||
def __init__(self):
|
def __init__(self) -> None:
|
||||||
""" 构造方法 """
|
""" 构造方法 """
|
||||||
self.front, self.rear = None, None # 头结点 front ,尾结点 rear
|
self.front: Optional[ListNode] = None # 头结点 front
|
||||||
self.__size = 0 # 双向队列的长度
|
self.rear: Optional[ListNode] = None # 尾结点 rear
|
||||||
|
self.__size: int = 0 # 双向队列的长度
|
||||||
|
|
||||||
def size(self):
|
def size(self) -> int:
|
||||||
""" 获取双向队列的长度 """
|
""" 获取双向队列的长度 """
|
||||||
return self.__size
|
return self.__size
|
||||||
|
|
||||||
def is_empty(self):
|
def is_empty(self) -> bool:
|
||||||
""" 判断双向队列是否为空 """
|
""" 判断双向队列是否为空 """
|
||||||
return self.size() == 0
|
return self.size() == 0
|
||||||
|
|
||||||
def push(self, num, is_front):
|
def push(self, num: int, is_front: bool) -> None:
|
||||||
""" 入队操作 """
|
""" 入队操作 """
|
||||||
node = ListNode(num)
|
node = ListNode(num)
|
||||||
# 若链表为空,则令 front, rear 都指向 node
|
# 若链表为空,则令 front, rear 都指向 node
|
||||||
@ -53,33 +52,33 @@ class LinkedListDeque:
|
|||||||
self.rear = node # 更新尾结点
|
self.rear = node # 更新尾结点
|
||||||
self.__size += 1 # 更新队列长度
|
self.__size += 1 # 更新队列长度
|
||||||
|
|
||||||
def push_first(self, num):
|
def push_first(self, num: int) -> None:
|
||||||
""" 队首入队 """
|
""" 队首入队 """
|
||||||
self.push(num, True)
|
self.push(num, True)
|
||||||
|
|
||||||
def push_last(self, num):
|
def push_last(self, num: int) -> None:
|
||||||
""" 队尾入队 """
|
""" 队尾入队 """
|
||||||
self.push(num, False)
|
self.push(num, False)
|
||||||
|
|
||||||
def poll(self, is_front):
|
def poll(self, is_front: bool) -> int:
|
||||||
""" 出队操作 """
|
""" 出队操作 """
|
||||||
# 若队列为空,直接返回 None
|
# 若队列为空,直接返回 None
|
||||||
if self.is_empty():
|
if self.is_empty():
|
||||||
return None
|
return None
|
||||||
# 队首出队操作
|
# 队首出队操作
|
||||||
if is_front:
|
if is_front:
|
||||||
val = self.front.val # 暂存头结点值
|
val: int = self.front.val # 暂存头结点值
|
||||||
# 删除头结点
|
# 删除头结点
|
||||||
fnext = self.front.next
|
fnext: Optional[ListNode] = self.front.next
|
||||||
if fnext != None:
|
if fnext != None:
|
||||||
fnext.prev = None
|
fnext.prev = None
|
||||||
self.front.next = None
|
self.front.next = None
|
||||||
self.front = fnext # 更新头结点
|
self.front = fnext # 更新头结点
|
||||||
# 队尾出队操作
|
# 队尾出队操作
|
||||||
else:
|
else:
|
||||||
val = self.rear.val # 暂存尾结点值
|
val: int = self.rear.val # 暂存尾结点值
|
||||||
# 删除尾结点
|
# 删除尾结点
|
||||||
rprev = self.rear.prev
|
rprev: Optional[ListNode] = self.rear.prev
|
||||||
if rprev != None:
|
if rprev != None:
|
||||||
rprev.next = None
|
rprev.next = None
|
||||||
self.rear.prev = None
|
self.rear.prev = None
|
||||||
@ -87,26 +86,26 @@ class LinkedListDeque:
|
|||||||
self.__size -= 1 # 更新队列长度
|
self.__size -= 1 # 更新队列长度
|
||||||
return val
|
return val
|
||||||
|
|
||||||
def poll_first(self):
|
def poll_first(self) -> int:
|
||||||
""" 队首出队 """
|
""" 队首出队 """
|
||||||
return self.poll(True)
|
return self.poll(True)
|
||||||
|
|
||||||
def poll_last(self):
|
def poll_last(self) -> int:
|
||||||
""" 队尾出队 """
|
""" 队尾出队 """
|
||||||
return self.poll(False)
|
return self.poll(False)
|
||||||
|
|
||||||
def peek_first(self):
|
def peek_first(self) -> int:
|
||||||
""" 访问队首元素 """
|
""" 访问队首元素 """
|
||||||
return None if self.is_empty() else self.front.val
|
return None if self.is_empty() else self.front.val
|
||||||
|
|
||||||
def peek_last(self):
|
def peek_last(self) -> int:
|
||||||
""" 访问队尾元素 """
|
""" 访问队尾元素 """
|
||||||
return None if self.is_empty() else self.rear.val
|
return None if self.is_empty() else self.rear.val
|
||||||
|
|
||||||
def to_array(self):
|
def to_array(self) -> List[int]:
|
||||||
""" 返回数组用于打印 """
|
""" 返回数组用于打印 """
|
||||||
node = self.front
|
node: Optional[ListNode] = self.front
|
||||||
res = [0] * self.size()
|
res: List[int] = [0] * self.size()
|
||||||
for i in range(self.size()):
|
for i in range(self.size()):
|
||||||
res[i] = node.val
|
res[i] = node.val
|
||||||
node = node.next
|
node = node.next
|
||||||
@ -123,9 +122,9 @@ if __name__ == "__main__":
|
|||||||
print("双向队列 deque =", deque.to_array())
|
print("双向队列 deque =", deque.to_array())
|
||||||
|
|
||||||
""" 访问元素 """
|
""" 访问元素 """
|
||||||
peek_first = deque.peek_first()
|
peek_first: int = deque.peek_first()
|
||||||
print("队首元素 peek_first =", peek_first)
|
print("队首元素 peek_first =", peek_first)
|
||||||
peek_last = deque.peek_last()
|
peek_last: int = deque.peek_last()
|
||||||
print("队尾元素 peek_last =", peek_last)
|
print("队尾元素 peek_last =", peek_last)
|
||||||
|
|
||||||
""" 元素入队 """
|
""" 元素入队 """
|
||||||
@ -135,15 +134,15 @@ if __name__ == "__main__":
|
|||||||
print("元素 1 队首入队后 deque =", deque.to_array())
|
print("元素 1 队首入队后 deque =", deque.to_array())
|
||||||
|
|
||||||
""" 元素出队 """
|
""" 元素出队 """
|
||||||
poll_last = deque.poll_last()
|
poll_last: int = deque.poll_last()
|
||||||
print("队尾出队元素 =", poll_last, ",队尾出队后 deque =", deque.to_array())
|
print("队尾出队元素 =", poll_last, ",队尾出队后 deque =", deque.to_array())
|
||||||
poll_first = deque.poll_first()
|
poll_first: int = deque.poll_first()
|
||||||
print("队首出队元素 =", poll_first, ",队首出队后 deque =", deque.to_array())
|
print("队首出队元素 =", poll_first, ",队首出队后 deque =", deque.to_array())
|
||||||
|
|
||||||
""" 获取双向队列的长度 """
|
""" 获取双向队列的长度 """
|
||||||
size = deque.size()
|
size: int = deque.size()
|
||||||
print("双向队列长度 size =", size)
|
print("双向队列长度 size =", size)
|
||||||
|
|
||||||
""" 判断双向队列是否为空 """
|
""" 判断双向队列是否为空 """
|
||||||
is_empty = deque.is_empty()
|
is_empty: bool = deque.is_empty()
|
||||||
print("双向队列是否为空 =", is_empty)
|
print("双向队列是否为空 =", is_empty)
|
||||||
|
@ -4,9 +4,7 @@ Created Time: 2022-12-01
|
|||||||
Author: Peng Chen (pengchzn@gmail.com)
|
Author: Peng Chen (pengchzn@gmail.com)
|
||||||
"""
|
"""
|
||||||
|
|
||||||
import os.path as osp
|
import sys, os.path as osp
|
||||||
import sys
|
|
||||||
|
|
||||||
sys.path.append(osp.dirname(osp.dirname(osp.abspath(__file__))))
|
sys.path.append(osp.dirname(osp.dirname(osp.abspath(__file__))))
|
||||||
from modules import *
|
from modules import *
|
||||||
|
|
||||||
@ -14,19 +12,19 @@ class LinkedListQueue:
|
|||||||
""" 基于链表实现的队列 """
|
""" 基于链表实现的队列 """
|
||||||
def __init__(self):
|
def __init__(self):
|
||||||
""" 构造方法 """
|
""" 构造方法 """
|
||||||
self.__front = None # 头结点 front
|
self.__front: Optional[ListNode] = None # 头结点 front
|
||||||
self.__rear = None # 尾结点 rear
|
self.__rear: Optional[ListNode] = None # 尾结点 rear
|
||||||
self.__size = 0
|
self.__size: int = 0
|
||||||
|
|
||||||
def size(self):
|
def size(self) -> int:
|
||||||
""" 获取队列的长度 """
|
""" 获取队列的长度 """
|
||||||
return self.__size
|
return self.__size
|
||||||
|
|
||||||
def is_empty(self):
|
def is_empty(self) -> bool:
|
||||||
""" 判断队列是否为空 """
|
""" 判断队列是否为空 """
|
||||||
return not self.__front
|
return not self.__front
|
||||||
|
|
||||||
def push(self, num):
|
def push(self, num: int) -> None:
|
||||||
""" 入队 """
|
""" 入队 """
|
||||||
# 尾结点后添加 num
|
# 尾结点后添加 num
|
||||||
node = ListNode(num)
|
node = ListNode(num)
|
||||||
@ -40,7 +38,7 @@ class LinkedListQueue:
|
|||||||
self.__rear = node
|
self.__rear = node
|
||||||
self.__size += 1
|
self.__size += 1
|
||||||
|
|
||||||
def poll(self):
|
def poll(self) -> int:
|
||||||
""" 出队 """
|
""" 出队 """
|
||||||
num = self.peek()
|
num = self.peek()
|
||||||
# 删除头结点
|
# 删除头结点
|
||||||
@ -48,14 +46,14 @@ class LinkedListQueue:
|
|||||||
self.__size -= 1
|
self.__size -= 1
|
||||||
return num
|
return num
|
||||||
|
|
||||||
def peek(self):
|
def peek(self) -> int:
|
||||||
""" 访问队首元素 """
|
""" 访问队首元素 """
|
||||||
if self.size() == 0:
|
if self.size() == 0:
|
||||||
print("队列为空")
|
print("队列为空")
|
||||||
return False
|
return False
|
||||||
return self.__front.val
|
return self.__front.val
|
||||||
|
|
||||||
def to_list(self):
|
def to_list(self) -> List[int]:
|
||||||
""" 转化为列表用于打印 """
|
""" 转化为列表用于打印 """
|
||||||
queue = []
|
queue = []
|
||||||
temp = self.__front
|
temp = self.__front
|
||||||
@ -79,18 +77,18 @@ if __name__ == "__main__":
|
|||||||
print("队列 queue =", queue.to_list())
|
print("队列 queue =", queue.to_list())
|
||||||
|
|
||||||
""" 访问队首元素 """
|
""" 访问队首元素 """
|
||||||
peek = queue.peek()
|
peek: int = queue.peek()
|
||||||
print("队首元素 front =", peek)
|
print("队首元素 front =", peek)
|
||||||
|
|
||||||
""" 元素出队 """
|
""" 元素出队 """
|
||||||
pop_front = queue.poll()
|
pop_front: int = queue.poll()
|
||||||
print("出队元素 poll =", pop_front)
|
print("出队元素 poll =", pop_front)
|
||||||
print("出队后 queue =", queue.to_list())
|
print("出队后 queue =", queue.to_list())
|
||||||
|
|
||||||
""" 获取队列的长度 """
|
""" 获取队列的长度 """
|
||||||
size = queue.size()
|
size: int = queue.size()
|
||||||
print("队列长度 size =", size)
|
print("队列长度 size =", size)
|
||||||
|
|
||||||
""" 判断队列是否为空 """
|
""" 判断队列是否为空 """
|
||||||
is_empty = queue.is_empty()
|
is_empty: bool = queue.is_empty()
|
||||||
print("队列是否为空 =", is_empty)
|
print("队列是否为空 =", is_empty)
|
||||||
|
@ -12,40 +12,40 @@ class LinkedListStack:
|
|||||||
""" 基于链表实现的栈 """
|
""" 基于链表实现的栈 """
|
||||||
def __init__(self):
|
def __init__(self):
|
||||||
""" 构造方法 """
|
""" 构造方法 """
|
||||||
self.__peek = None
|
self.__peek: Optional[ListNode] = None
|
||||||
self.__size = 0
|
self.__size: int = 0
|
||||||
|
|
||||||
def size(self):
|
def size(self) -> int:
|
||||||
""" 获取栈的长度 """
|
""" 获取栈的长度 """
|
||||||
return self.__size
|
return self.__size
|
||||||
|
|
||||||
def is_empty(self):
|
def is_empty(self) -> bool:
|
||||||
""" 判断栈是否为空 """
|
""" 判断栈是否为空 """
|
||||||
return not self.__peek
|
return not self.__peek
|
||||||
|
|
||||||
def push(self, val):
|
def push(self, val: int) -> None:
|
||||||
""" 入栈 """
|
""" 入栈 """
|
||||||
node = ListNode(val)
|
node = ListNode(val)
|
||||||
node.next = self.__peek
|
node.next = self.__peek
|
||||||
self.__peek = node
|
self.__peek = node
|
||||||
self.__size += 1
|
self.__size += 1
|
||||||
|
|
||||||
def pop(self):
|
def pop(self) -> int:
|
||||||
""" 出栈 """
|
""" 出栈 """
|
||||||
num = self.peek()
|
num: int = self.peek()
|
||||||
self.__peek = self.__peek.next
|
self.__peek = self.__peek.next
|
||||||
self.__size -= 1
|
self.__size -= 1
|
||||||
return num
|
return num
|
||||||
|
|
||||||
def peek(self):
|
def peek(self) -> int:
|
||||||
""" 访问栈顶元素 """
|
""" 访问栈顶元素 """
|
||||||
# 判空处理
|
# 判空处理
|
||||||
if not self.__peek: return None
|
if not self.__peek: return None
|
||||||
return self.__peek.val
|
return self.__peek.val
|
||||||
|
|
||||||
def to_list(self):
|
def to_list(self) -> List[int]:
|
||||||
""" 转化为列表用于打印 """
|
""" 转化为列表用于打印 """
|
||||||
arr = []
|
arr: List[int] = []
|
||||||
node = self.__peek
|
node = self.__peek
|
||||||
while node:
|
while node:
|
||||||
arr.append(node.val)
|
arr.append(node.val)
|
||||||
@ -68,18 +68,18 @@ if __name__ == "__main__":
|
|||||||
print("栈 stack =", stack.to_list())
|
print("栈 stack =", stack.to_list())
|
||||||
|
|
||||||
""" 访问栈顶元素 """
|
""" 访问栈顶元素 """
|
||||||
peek = stack.peek()
|
peek: int = stack.peek()
|
||||||
print("栈顶元素 peek =", peek)
|
print("栈顶元素 peek =", peek)
|
||||||
|
|
||||||
""" 元素出栈 """
|
""" 元素出栈 """
|
||||||
pop = stack.pop()
|
pop: int = stack.pop()
|
||||||
print("出栈元素 pop =", pop)
|
print("出栈元素 pop =", pop)
|
||||||
print("出栈后 stack =", stack.to_list())
|
print("出栈后 stack =", stack.to_list())
|
||||||
|
|
||||||
""" 获取栈的长度 """
|
""" 获取栈的长度 """
|
||||||
size = stack.size()
|
size: int = stack.size()
|
||||||
print("栈的长度 size =", size)
|
print("栈的长度 size =", size)
|
||||||
|
|
||||||
""" 判断是否为空 """
|
""" 判断是否为空 """
|
||||||
is_empty = stack.is_empty()
|
is_empty: bool = stack.is_empty()
|
||||||
print("栈是否为空 =", is_empty)
|
print("栈是否为空 =", is_empty)
|
||||||
|
@ -4,9 +4,7 @@ Created Time: 2022-11-29
|
|||||||
Author: Peng Chen (pengchzn@gmail.com)
|
Author: Peng Chen (pengchzn@gmail.com)
|
||||||
"""
|
"""
|
||||||
|
|
||||||
import os.path as osp
|
import sys, os.path as osp
|
||||||
import sys
|
|
||||||
|
|
||||||
sys.path.append(osp.dirname(osp.dirname(osp.abspath(__file__))))
|
sys.path.append(osp.dirname(osp.dirname(osp.abspath(__file__))))
|
||||||
from modules import *
|
from modules import *
|
||||||
|
|
||||||
@ -14,9 +12,9 @@ from modules import *
|
|||||||
""" Driver Code """
|
""" Driver Code """
|
||||||
if __name__ == "__main__":
|
if __name__ == "__main__":
|
||||||
""" 初始化队列 """
|
""" 初始化队列 """
|
||||||
# 在 Python 中,我们一般将双向队列类 deque 看左队列使用
|
# 在 Python 中,我们一般将双向队列类 deque 看作队列使用
|
||||||
# 虽然 queue.Queue() 是纯正的队列类,但不太好用,因此不建议
|
# 虽然 queue.Queue() 是纯正的队列类,但不太好用
|
||||||
que = collections.deque()
|
que: Deque[int] = collections.deque()
|
||||||
|
|
||||||
""" 元素入队 """
|
""" 元素入队 """
|
||||||
que.append(1)
|
que.append(1)
|
||||||
@ -27,18 +25,18 @@ if __name__ == "__main__":
|
|||||||
print("队列 que =", que)
|
print("队列 que =", que)
|
||||||
|
|
||||||
""" 访问队首元素 """
|
""" 访问队首元素 """
|
||||||
front = que[0];
|
front: int = que[0]
|
||||||
print("队首元素 front =", front);
|
print("队首元素 front =", front)
|
||||||
|
|
||||||
""" 元素出队 """
|
""" 元素出队 """
|
||||||
pop = que.popleft()
|
pop: int = que.popleft()
|
||||||
print("出队元素 pop =", pop)
|
print("出队元素 pop =", pop)
|
||||||
print("出队后 que =", que)
|
print("出队后 que =", que)
|
||||||
|
|
||||||
""" 获取队列的长度 """
|
""" 获取队列的长度 """
|
||||||
size = len(que)
|
size: int = len(que)
|
||||||
print("队列长度 size =", size)
|
print("队列长度 size =", size)
|
||||||
|
|
||||||
""" 判断队列是否为空 """
|
""" 判断队列是否为空 """
|
||||||
is_empty = len(que) == 0
|
is_empty: bool = len(que) == 0
|
||||||
print("队列是否为空 =", is_empty)
|
print("队列是否为空 =", is_empty)
|
||||||
|
@ -13,7 +13,7 @@ from modules import *
|
|||||||
if __name__ == "__main__":
|
if __name__ == "__main__":
|
||||||
""" 初始化栈 """
|
""" 初始化栈 """
|
||||||
# Python 没有内置的栈类,可以把 list 当作栈来使用
|
# Python 没有内置的栈类,可以把 list 当作栈来使用
|
||||||
stack = []
|
stack: List[int] = []
|
||||||
|
|
||||||
""" 元素入栈 """
|
""" 元素入栈 """
|
||||||
stack.append(1)
|
stack.append(1)
|
||||||
@ -24,18 +24,18 @@ if __name__ == "__main__":
|
|||||||
print("栈 stack =", stack)
|
print("栈 stack =", stack)
|
||||||
|
|
||||||
""" 访问栈顶元素 """
|
""" 访问栈顶元素 """
|
||||||
peek = stack[-1]
|
peek: int = stack[-1]
|
||||||
print("栈顶元素 peek =", peek)
|
print("栈顶元素 peek =", peek)
|
||||||
|
|
||||||
""" 元素出栈 """
|
""" 元素出栈 """
|
||||||
pop = stack.pop()
|
pop: int = stack.pop()
|
||||||
print("出栈元素 pop =", pop)
|
print("出栈元素 pop =", pop)
|
||||||
print("出栈后 stack =", stack)
|
print("出栈后 stack =", stack)
|
||||||
|
|
||||||
""" 获取栈的长度 """
|
""" 获取栈的长度 """
|
||||||
size = len(stack)
|
size: int = len(stack)
|
||||||
print("栈的长度 size =", size)
|
print("栈的长度 size =", size)
|
||||||
|
|
||||||
""" 判断是否为空 """
|
""" 判断是否为空 """
|
||||||
is_empty = len(stack) == 0
|
is_empty: bool = len(stack) == 0
|
||||||
print("栈是否为空 =", is_empty)
|
print("栈是否为空 =", is_empty)
|
||||||
|
@ -12,7 +12,11 @@ class AVLTree:
|
|||||||
""" AVL 树 """
|
""" AVL 树 """
|
||||||
def __init__(self, root: Optional[TreeNode] = None):
|
def __init__(self, root: Optional[TreeNode] = None):
|
||||||
""" 构造方法 """
|
""" 构造方法 """
|
||||||
self.root = root
|
self.__root = root
|
||||||
|
|
||||||
|
@property
|
||||||
|
def root(self) -> Optional[TreeNode]:
|
||||||
|
return self.__root
|
||||||
|
|
||||||
def height(self, node: Optional[TreeNode]) -> int:
|
def height(self, node: Optional[TreeNode]) -> int:
|
||||||
""" 获取结点高度 """
|
""" 获取结点高度 """
|
||||||
@ -34,7 +38,7 @@ class AVLTree:
|
|||||||
# 结点平衡因子 = 左子树高度 - 右子树高度
|
# 结点平衡因子 = 左子树高度 - 右子树高度
|
||||||
return self.height(node.left) - self.height(node.right)
|
return self.height(node.left) - self.height(node.right)
|
||||||
|
|
||||||
def __right_rotate(self, node: Optional[TreeNode]) -> TreeNode:
|
def __right_rotate(self, node: Optional[TreeNode]) -> Optional[TreeNode]:
|
||||||
""" 右旋操作 """
|
""" 右旋操作 """
|
||||||
child = node.left
|
child = node.left
|
||||||
grand_child = child.right
|
grand_child = child.right
|
||||||
@ -47,7 +51,7 @@ class AVLTree:
|
|||||||
# 返回旋转后子树的根结点
|
# 返回旋转后子树的根结点
|
||||||
return child
|
return child
|
||||||
|
|
||||||
def __left_rotate(self, node: Optional[TreeNode]) -> TreeNode:
|
def __left_rotate(self, node: Optional[TreeNode]) -> Optional[TreeNode]:
|
||||||
""" 左旋操作 """
|
""" 左旋操作 """
|
||||||
child = node.right
|
child = node.right
|
||||||
grand_child = child.left
|
grand_child = child.left
|
||||||
@ -60,7 +64,7 @@ class AVLTree:
|
|||||||
# 返回旋转后子树的根结点
|
# 返回旋转后子树的根结点
|
||||||
return child
|
return child
|
||||||
|
|
||||||
def __rotate(self, node: Optional[TreeNode]) -> TreeNode:
|
def __rotate(self, node: Optional[TreeNode]) -> Optional[TreeNode]:
|
||||||
""" 执行旋转操作,使该子树重新恢复平衡 """
|
""" 执行旋转操作,使该子树重新恢复平衡 """
|
||||||
# 获取结点 node 的平衡因子
|
# 获取结点 node 的平衡因子
|
||||||
balance_factor = self.balance_factor(node)
|
balance_factor = self.balance_factor(node)
|
||||||
@ -87,8 +91,8 @@ class AVLTree:
|
|||||||
|
|
||||||
def insert(self, val) -> TreeNode:
|
def insert(self, val) -> TreeNode:
|
||||||
""" 插入结点 """
|
""" 插入结点 """
|
||||||
self.root = self.__insert_helper(self.root, val)
|
self.__root = self.__insert_helper(self.__root, val)
|
||||||
return self.root
|
return self.__root
|
||||||
|
|
||||||
def __insert_helper(self, node: Optional[TreeNode], val: int) -> TreeNode:
|
def __insert_helper(self, node: Optional[TreeNode], val: int) -> TreeNode:
|
||||||
""" 递归插入结点(辅助方法)"""
|
""" 递归插入结点(辅助方法)"""
|
||||||
@ -107,10 +111,10 @@ class AVLTree:
|
|||||||
# 2. 执行旋转操作,使该子树重新恢复平衡
|
# 2. 执行旋转操作,使该子树重新恢复平衡
|
||||||
return self.__rotate(node)
|
return self.__rotate(node)
|
||||||
|
|
||||||
def remove(self, val: int):
|
def remove(self, val: int) -> Optional[TreeNode]:
|
||||||
""" 删除结点 """
|
""" 删除结点 """
|
||||||
root = self.__remove_helper(self.root, val)
|
self.__root = self.__remove_helper(self.__root, val)
|
||||||
return root
|
return self.__root
|
||||||
|
|
||||||
def __remove_helper(self, node: Optional[TreeNode], val: int) -> Optional[TreeNode]:
|
def __remove_helper(self, node: Optional[TreeNode], val: int) -> Optional[TreeNode]:
|
||||||
""" 递归删除结点(辅助方法) """
|
""" 递归删除结点(辅助方法) """
|
||||||
@ -148,9 +152,9 @@ class AVLTree:
|
|||||||
node = node.left
|
node = node.left
|
||||||
return node
|
return node
|
||||||
|
|
||||||
def search(self, val: int):
|
def search(self, val: int) -> Optional[TreeNode]:
|
||||||
""" 查找结点 """
|
""" 查找结点 """
|
||||||
cur = self.root
|
cur = self.__root
|
||||||
# 循环查找,越过叶结点后跳出
|
# 循环查找,越过叶结点后跳出
|
||||||
while cur is not None:
|
while cur is not None:
|
||||||
# 目标结点在 cur 的右子树中
|
# 目标结点在 cur 的右子树中
|
||||||
|
@ -22,7 +22,7 @@ class BinarySearchTree:
|
|||||||
return None
|
return None
|
||||||
|
|
||||||
# 将数组中间结点作为根结点
|
# 将数组中间结点作为根结点
|
||||||
mid = (start_index + end_index) // 2
|
mid: int = (start_index + end_index) // 2
|
||||||
root = TreeNode(nums[mid])
|
root = TreeNode(nums[mid])
|
||||||
# 递归建立左子树和右子树
|
# 递归建立左子树和右子树
|
||||||
root.left = self.build_tree(nums=nums, start_index=start_index, end_index=mid - 1)
|
root.left = self.build_tree(nums=nums, start_index=start_index, end_index=mid - 1)
|
||||||
@ -35,7 +35,7 @@ class BinarySearchTree:
|
|||||||
|
|
||||||
def search(self, num: int) -> Optional[TreeNode]:
|
def search(self, num: int) -> Optional[TreeNode]:
|
||||||
""" 查找结点 """
|
""" 查找结点 """
|
||||||
cur = self.root
|
cur: Optional[TreeNode] = self.__root
|
||||||
# 循环查找,越过叶结点后跳出
|
# 循环查找,越过叶结点后跳出
|
||||||
while cur is not None:
|
while cur is not None:
|
||||||
# 目标结点在 cur 的右子树中
|
# 目标结点在 cur 的右子树中
|
||||||
@ -51,13 +51,12 @@ class BinarySearchTree:
|
|||||||
|
|
||||||
def insert(self, num: int) -> Optional[TreeNode]:
|
def insert(self, num: int) -> Optional[TreeNode]:
|
||||||
""" 插入结点 """
|
""" 插入结点 """
|
||||||
root = self.root
|
|
||||||
# 若树为空,直接提前返回
|
# 若树为空,直接提前返回
|
||||||
if root is None:
|
if self.__root is None:
|
||||||
return None
|
return None
|
||||||
|
|
||||||
# 循环查找,越过叶结点后跳出
|
# 循环查找,越过叶结点后跳出
|
||||||
cur, pre = root, None
|
cur, pre = self.__root, None
|
||||||
while cur is not None:
|
while cur is not None:
|
||||||
# 找到重复结点,直接返回
|
# 找到重复结点,直接返回
|
||||||
if cur.val == num:
|
if cur.val == num:
|
||||||
@ -80,13 +79,12 @@ class BinarySearchTree:
|
|||||||
|
|
||||||
def remove(self, num: int) -> Optional[TreeNode]:
|
def remove(self, num: int) -> Optional[TreeNode]:
|
||||||
""" 删除结点 """
|
""" 删除结点 """
|
||||||
root = self.root
|
|
||||||
# 若树为空,直接提前返回
|
# 若树为空,直接提前返回
|
||||||
if root is None:
|
if self.__root is None:
|
||||||
return None
|
return None
|
||||||
|
|
||||||
# 循环查找,越过叶结点后跳出
|
# 循环查找,越过叶结点后跳出
|
||||||
cur, pre = root, None
|
cur, pre = self.__root, None
|
||||||
while cur is not None:
|
while cur is not None:
|
||||||
# 找到待删除结点,跳出循环
|
# 找到待删除结点,跳出循环
|
||||||
if cur.val == num:
|
if cur.val == num:
|
||||||
@ -112,8 +110,8 @@ class BinarySearchTree:
|
|||||||
# 子结点数量 = 2
|
# 子结点数量 = 2
|
||||||
else:
|
else:
|
||||||
# 获取中序遍历中 cur 的下一个结点
|
# 获取中序遍历中 cur 的下一个结点
|
||||||
nex = self.get_inorder_next(cur.right)
|
nex: TreeNode = self.get_inorder_next(cur.right)
|
||||||
tmp = nex.val
|
tmp: int = nex.val
|
||||||
# 递归删除结点 nex
|
# 递归删除结点 nex
|
||||||
self.remove(nex.val)
|
self.remove(nex.val)
|
||||||
# 将 nex 的值复制给 cur
|
# 将 nex 的值复制给 cur
|
||||||
@ -143,7 +141,7 @@ if __name__ == "__main__":
|
|||||||
print("\n查找到的结点对象为: {},结点值 = {}".format(node, node.val))
|
print("\n查找到的结点对象为: {},结点值 = {}".format(node, node.val))
|
||||||
|
|
||||||
# 插入结点
|
# 插入结点
|
||||||
ndoe = bst.insert(16)
|
node = bst.insert(16)
|
||||||
print("\n插入结点 16 后,二叉树为\n")
|
print("\n插入结点 16 后,二叉树为\n")
|
||||||
print_tree(bst.root)
|
print_tree(bst.root)
|
||||||
|
|
||||||
|
@ -9,20 +9,20 @@ sys.path.append(osp.dirname(osp.dirname(osp.abspath(__file__))))
|
|||||||
from modules import *
|
from modules import *
|
||||||
|
|
||||||
|
|
||||||
def level_order(root: Optional[TreeNode]):
|
def level_order(root: Optional[TreeNode]) -> List[int]:
|
||||||
""" 层序遍历 """
|
""" 层序遍历 """
|
||||||
# 初始化队列,加入根结点
|
# 初始化队列,加入根结点
|
||||||
queue = collections.deque()
|
queue: Deque[TreeNode] = collections.deque()
|
||||||
queue.append(root)
|
queue.append(root)
|
||||||
# 初始化一个列表,用于保存遍历序列
|
# 初始化一个列表,用于保存遍历序列
|
||||||
res = []
|
res: List[int] = []
|
||||||
while queue:
|
while queue:
|
||||||
node = queue.popleft() # 队列出队
|
node: TreeNode = queue.popleft() # 队列出队
|
||||||
res.append(node.val) # 保存结点值
|
res.append(node.val) # 保存结点值
|
||||||
if node.left is not None:
|
if node.left is not None:
|
||||||
queue.append(node.left) # 左子结点入队
|
queue.append(node.left) # 左子结点入队
|
||||||
if node.right is not None:
|
if node.right is not None:
|
||||||
queue.append(node.right) # 右子结点入队
|
queue.append(node.right) # 右子结点入队
|
||||||
return res
|
return res
|
||||||
|
|
||||||
|
|
||||||
@ -30,11 +30,11 @@ def level_order(root: Optional[TreeNode]):
|
|||||||
if __name__ == "__main__":
|
if __name__ == "__main__":
|
||||||
# 初始化二叉树
|
# 初始化二叉树
|
||||||
# 这里借助了一个从数组直接生成二叉树的函数
|
# 这里借助了一个从数组直接生成二叉树的函数
|
||||||
root = list_to_tree(arr=[1, 2, 3, 4, 5, 6, 7])
|
root: TreeNode = list_to_tree(arr=[1, 2, 3, 4, 5, 6, 7])
|
||||||
print("\n初始化二叉树\n")
|
print("\n初始化二叉树\n")
|
||||||
print_tree(root)
|
print_tree(root)
|
||||||
|
|
||||||
# 层序遍历
|
# 层序遍历
|
||||||
res = level_order(root)
|
res: List[int] = level_order(root)
|
||||||
print("\n层序遍历的结点打印序列 = ", res)
|
print("\n层序遍历的结点打印序列 = ", res)
|
||||||
assert res == [1, 2, 3, 4, 5, 6, 7]
|
assert res == [1, 2, 3, 4, 5, 6, 7]
|
||||||
|
@ -9,7 +9,7 @@ sys.path.append(osp.dirname(osp.dirname(osp.abspath(__file__))))
|
|||||||
from modules import *
|
from modules import *
|
||||||
|
|
||||||
|
|
||||||
def pre_order(root: Optional[TreeNode]):
|
def pre_order(root: Optional[TreeNode]) -> None:
|
||||||
""" 前序遍历 """
|
""" 前序遍历 """
|
||||||
if root is None:
|
if root is None:
|
||||||
return
|
return
|
||||||
@ -18,7 +18,7 @@ def pre_order(root: Optional[TreeNode]):
|
|||||||
pre_order(root=root.left)
|
pre_order(root=root.left)
|
||||||
pre_order(root=root.right)
|
pre_order(root=root.right)
|
||||||
|
|
||||||
def in_order(root: Optional[TreeNode]):
|
def in_order(root: Optional[TreeNode]) -> None:
|
||||||
""" 中序遍历 """
|
""" 中序遍历 """
|
||||||
if root is None:
|
if root is None:
|
||||||
return
|
return
|
||||||
@ -27,7 +27,7 @@ def in_order(root: Optional[TreeNode]):
|
|||||||
res.append(root.val)
|
res.append(root.val)
|
||||||
in_order(root=root.right)
|
in_order(root=root.right)
|
||||||
|
|
||||||
def post_order(root: Optional[TreeNode]):
|
def post_order(root: Optional[TreeNode]) -> None:
|
||||||
""" 后序遍历 """
|
""" 后序遍历 """
|
||||||
if root is None:
|
if root is None:
|
||||||
return
|
return
|
||||||
@ -36,7 +36,6 @@ def post_order(root: Optional[TreeNode]):
|
|||||||
post_order(root=root.right)
|
post_order(root=root.right)
|
||||||
res.append(root.val)
|
res.append(root.val)
|
||||||
|
|
||||||
res = []
|
|
||||||
|
|
||||||
""" Driver Code """
|
""" Driver Code """
|
||||||
if __name__ == "__main__":
|
if __name__ == "__main__":
|
||||||
@ -47,7 +46,7 @@ if __name__ == "__main__":
|
|||||||
print_tree(root)
|
print_tree(root)
|
||||||
|
|
||||||
# 前序遍历
|
# 前序遍历
|
||||||
res.clear()
|
res = []
|
||||||
pre_order(root)
|
pre_order(root)
|
||||||
print("\n前序遍历的结点打印序列 = ", res)
|
print("\n前序遍历的结点打印序列 = ", res)
|
||||||
assert res == [1, 2, 4, 5, 3, 6, 7]
|
assert res == [1, 2, 4, 5, 3, 6, 7]
|
||||||
|
@ -5,7 +5,7 @@ import queue
|
|||||||
import random
|
import random
|
||||||
import functools
|
import functools
|
||||||
import collections
|
import collections
|
||||||
from typing import Optional, List, Dict, DefaultDict, OrderedDict, Set, Deque
|
from typing import Optional, Tuple, List, Dict, DefaultDict, OrderedDict, Set, Deque
|
||||||
from .linked_list import ListNode, list_to_linked_list, linked_list_to_list, get_list_node
|
from .linked_list import ListNode, list_to_linked_list, linked_list_to_list, get_list_node
|
||||||
from .binary_tree import TreeNode, list_to_tree, tree_to_list, get_tree_node
|
from .binary_tree import TreeNode, list_to_tree, tree_to_list, get_tree_node
|
||||||
from .vertex import Vertex, vals_to_vets, vets_to_vals
|
from .vertex import Vertex, vals_to_vets, vets_to_vals
|
||||||
|
@ -5,36 +5,26 @@ Author: Krahets (krahets@163.com)
|
|||||||
"""
|
"""
|
||||||
|
|
||||||
import collections
|
import collections
|
||||||
|
from typing import List, Deque, Optional
|
||||||
|
|
||||||
class TreeNode:
|
class TreeNode:
|
||||||
"""Definition for a binary tree node
|
""" Definition for a binary tree node """
|
||||||
"""
|
def __init__(self, val: int = 0, left: Optional['TreeNode'] = None, right: Optional['TreeNode'] = None):
|
||||||
def __init__(self, val=0, left=None, right=None):
|
self.val: int = val # 结点值
|
||||||
self.val = val # 结点值
|
self.height: int = 0 # 结点高度
|
||||||
self.height = 0 # 结点高度
|
self.left: Optional[TreeNode] = left # 左子结点引用
|
||||||
self.left = left # 左子结点引用
|
self.right: Optional[TreeNode] = right # 右子结点引用
|
||||||
self.right = right # 右子结点引用
|
|
||||||
|
|
||||||
def __str__(self):
|
def list_to_tree(arr: List[int]) -> Optional[TreeNode]:
|
||||||
val = self.val
|
""" Generate a binary tree with a list """
|
||||||
left_node_val = self.left.val if self.left else None
|
|
||||||
right_node_val = self.right.val if self.right else None
|
|
||||||
return "<TreeNode: {}, leftTreeNode: {}, rightTreeNode: {}>".format(val, left_node_val, right_node_val)
|
|
||||||
|
|
||||||
__repr__ = __str__
|
|
||||||
|
|
||||||
|
|
||||||
def list_to_tree(arr):
|
|
||||||
"""Generate a binary tree with a list
|
|
||||||
"""
|
|
||||||
if not arr:
|
if not arr:
|
||||||
return None
|
return None
|
||||||
|
|
||||||
i = 0
|
i: int = 0
|
||||||
root = TreeNode(arr[0])
|
root = TreeNode(arr[0])
|
||||||
queue = collections.deque([root])
|
queue: Deque[TreeNode] = collections.deque([root])
|
||||||
while queue:
|
while queue:
|
||||||
node = queue.popleft()
|
node: TreeNode = queue.popleft()
|
||||||
i += 1
|
i += 1
|
||||||
if i >= len(arr): break
|
if i >= len(arr): break
|
||||||
if arr[i] != None:
|
if arr[i] != None:
|
||||||
@ -48,15 +38,14 @@ def list_to_tree(arr):
|
|||||||
|
|
||||||
return root
|
return root
|
||||||
|
|
||||||
def tree_to_list(root):
|
def tree_to_list(root: Optional[TreeNode]) -> List[int]:
|
||||||
"""Serialize a tree into an array
|
""" Serialize a tree into an array """
|
||||||
"""
|
|
||||||
if not root: return []
|
if not root: return []
|
||||||
queue = collections.deque()
|
queue: Deque[TreeNode] = collections.deque()
|
||||||
queue.append(root)
|
queue.append(root)
|
||||||
res = []
|
res: List[int] = []
|
||||||
while queue:
|
while queue:
|
||||||
node = queue.popleft()
|
node: Optional[TreeNode] = queue.popleft()
|
||||||
if node:
|
if node:
|
||||||
res.append(node.val)
|
res.append(node.val)
|
||||||
queue.append(node.left)
|
queue.append(node.left)
|
||||||
@ -64,13 +53,12 @@ def tree_to_list(root):
|
|||||||
else: res.append(None)
|
else: res.append(None)
|
||||||
return res
|
return res
|
||||||
|
|
||||||
def get_tree_node(root, val):
|
def get_tree_node(root: Optional[TreeNode], val: int) -> Optional[TreeNode]:
|
||||||
"""Get a tree node with specific value in a binary tree
|
""" Get a tree node with specific value in a binary tree """
|
||||||
"""
|
|
||||||
if not root:
|
if not root:
|
||||||
return
|
return
|
||||||
if root.val == val:
|
if root.val == val:
|
||||||
return root
|
return root
|
||||||
left = get_tree_node(root.left, val)
|
left: Optional[TreeNode] = get_tree_node(root.left, val)
|
||||||
right = get_tree_node(root.right, val)
|
right: Optional[TreeNode] = get_tree_node(root.right, val)
|
||||||
return left if left else right
|
return left if left else right
|
||||||
|
@ -4,22 +4,16 @@ Created Time: 2021-12-11
|
|||||||
Author: Krahets (krahets@163.com)
|
Author: Krahets (krahets@163.com)
|
||||||
"""
|
"""
|
||||||
|
|
||||||
|
from typing import List, Optional
|
||||||
|
|
||||||
class ListNode:
|
class ListNode:
|
||||||
"""Definition for a singly-linked list node
|
""" Definition for a singly-linked list node """
|
||||||
"""
|
def __init__(self, val: int):
|
||||||
def __init__(self, val=0, next=None):
|
self.val: int = val # 结点值
|
||||||
self.val = val
|
self.next: Optional[ListNode] = None # 后继结点引用
|
||||||
self.next = next
|
|
||||||
|
|
||||||
def list_to_linked_list(arr):
|
def list_to_linked_list(arr: List[int]) -> Optional[ListNode]:
|
||||||
"""Generate a linked list with a list
|
""" Generate a linked list with a list """
|
||||||
|
|
||||||
Args:
|
|
||||||
arr ([type]): [description]
|
|
||||||
|
|
||||||
Returns:
|
|
||||||
[type]: [description]
|
|
||||||
"""
|
|
||||||
dum = head = ListNode(0)
|
dum = head = ListNode(0)
|
||||||
for a in arr:
|
for a in arr:
|
||||||
node = ListNode(a)
|
node = ListNode(a)
|
||||||
@ -27,31 +21,16 @@ def list_to_linked_list(arr):
|
|||||||
head = head.next
|
head = head.next
|
||||||
return dum.next
|
return dum.next
|
||||||
|
|
||||||
def linked_list_to_list(head):
|
def linked_list_to_list(head: Optional[ListNode]) -> List[int]:
|
||||||
"""Serialize a linked list into an array
|
""" Serialize a linked list into an array """
|
||||||
|
arr: List[int] = []
|
||||||
Args:
|
|
||||||
head ([type]): [description]
|
|
||||||
|
|
||||||
Returns:
|
|
||||||
[type]: [description]
|
|
||||||
"""
|
|
||||||
arr = []
|
|
||||||
while head:
|
while head:
|
||||||
arr.append(head.val)
|
arr.append(head.val)
|
||||||
head = head.next
|
head = head.next
|
||||||
return arr
|
return arr
|
||||||
|
|
||||||
def get_list_node(head, val):
|
def get_list_node(head: Optional[ListNode], val: int) -> Optional[ListNode]:
|
||||||
"""Get a list node with specific value from a linked list
|
""" Get a list node with specific value from a linked list """
|
||||||
|
|
||||||
Args:
|
|
||||||
head ([type]): [description]
|
|
||||||
val ([type]): [description]
|
|
||||||
|
|
||||||
Returns:
|
|
||||||
[type]: [description]
|
|
||||||
"""
|
|
||||||
while head and head.val != val:
|
while head and head.val != val:
|
||||||
head = head.next
|
head = head.next
|
||||||
return head
|
return head
|
||||||
|
@ -4,57 +4,48 @@ Created Time: 2021-12-11
|
|||||||
Author: Krahets (krahets@163.com), msk397 (machangxinq@gmail.com)
|
Author: Krahets (krahets@163.com), msk397 (machangxinq@gmail.com)
|
||||||
"""
|
"""
|
||||||
|
|
||||||
from .binary_tree import TreeNode, tree_to_list, list_to_tree
|
from .binary_tree import TreeNode, list_to_tree
|
||||||
from .linked_list import ListNode, linked_list_to_list
|
from .linked_list import ListNode, linked_list_to_list
|
||||||
|
|
||||||
def print_matrix(mat):
|
from typing import List, Optional, Dict
|
||||||
"""Print a matrix
|
|
||||||
|
|
||||||
Args:
|
def print_matrix(mat: List[List[int]]) -> None:
|
||||||
mat ([type]): [description]
|
""" Print a matrix """
|
||||||
"""
|
s: List[str] = []
|
||||||
pstr = []
|
|
||||||
for arr in mat:
|
for arr in mat:
|
||||||
pstr.append(' ' + str(arr))
|
s.append(' ' + str(arr))
|
||||||
|
|
||||||
print('[\n' + ',\n'.join(pstr) + '\n]')
|
print('[\n' + ',\n'.join(s) + '\n]')
|
||||||
|
|
||||||
def print_linked_list(head):
|
def print_linked_list(head: Optional[ListNode]) -> None:
|
||||||
"""Print a linked list
|
""" Print a linked list """
|
||||||
|
arr: List[int] = linked_list_to_list(head)
|
||||||
Args:
|
|
||||||
head ([type]): [description]
|
|
||||||
"""
|
|
||||||
arr = linked_list_to_list(head)
|
|
||||||
print(' -> '.join([str(a) for a in arr]))
|
print(' -> '.join([str(a) for a in arr]))
|
||||||
|
|
||||||
class Trunk:
|
class Trunk:
|
||||||
def __init__(self, prev=None, str=None):
|
def __init__(self, prev: Optional['Trunk'] = None, string: Optional[str] = None) -> None:
|
||||||
self.prev = prev
|
self.prev: Optional[Trunk] = prev
|
||||||
self.str = str
|
self.str: Optional[str] = string
|
||||||
|
|
||||||
def show_trunks(p):
|
def show_trunks(p: Optional[Trunk]) -> None:
|
||||||
if p is None:
|
if p is None:
|
||||||
return
|
return
|
||||||
show_trunks(p.prev)
|
show_trunks(p.prev)
|
||||||
print(p.str, end='')
|
print(p.str, end='')
|
||||||
|
|
||||||
def print_tree(root, prev=None, is_left=False):
|
def print_tree(root: Optional[TreeNode], prev: Optional[Trunk] = None, is_left: bool = False) -> None:
|
||||||
"""Print a binary tree
|
"""
|
||||||
This tree printer is borrowed from TECHIE DELIGHT
|
Print a binary tree
|
||||||
https://www.techiedelight.com/c-program-print-binary-tree/
|
This tree printer is borrowed from TECHIE DELIGHT
|
||||||
Args:
|
https://www.techiedelight.com/c-program-print-binary-tree/
|
||||||
root ([type]): [description]
|
|
||||||
prev ([type], optional): [description]. Defaults to None.
|
|
||||||
is_left (bool, optional): [description]. Defaults to False.
|
|
||||||
"""
|
"""
|
||||||
if root is None:
|
if root is None:
|
||||||
return
|
return
|
||||||
|
|
||||||
prev_str = ' '
|
prev_str: str = ' '
|
||||||
trunk = Trunk(prev, prev_str)
|
trunk = Trunk(prev, prev_str)
|
||||||
print_tree(root.right, trunk, True)
|
print_tree(root.right, trunk, True)
|
||||||
|
|
||||||
if prev is None:
|
if prev is None:
|
||||||
trunk.str = '———'
|
trunk.str = '———'
|
||||||
elif is_left:
|
elif is_left:
|
||||||
@ -63,7 +54,7 @@ def print_tree(root, prev=None, is_left=False):
|
|||||||
else:
|
else:
|
||||||
trunk.str = '\———'
|
trunk.str = '\———'
|
||||||
prev.str = prev_str
|
prev.str = prev_str
|
||||||
|
|
||||||
show_trunks(trunk)
|
show_trunks(trunk)
|
||||||
print(' ' + str(root.val))
|
print(' ' + str(root.val))
|
||||||
if prev:
|
if prev:
|
||||||
@ -71,17 +62,14 @@ def print_tree(root, prev=None, is_left=False):
|
|||||||
trunk.str = ' |'
|
trunk.str = ' |'
|
||||||
print_tree(root.left, trunk, False)
|
print_tree(root.left, trunk, False)
|
||||||
|
|
||||||
def print_dict(d):
|
def print_dict(mapp: Dict) -> None:
|
||||||
"""Print a dict
|
""" Print a dict """
|
||||||
|
for key, value in mapp.items():
|
||||||
Args:
|
|
||||||
d ([type]): [description]
|
|
||||||
"""
|
|
||||||
for key, value in d.items():
|
|
||||||
print(key, '->', value)
|
print(key, '->', value)
|
||||||
|
|
||||||
def print_heap(heap):
|
def print_heap(heap: List[int]) -> None:
|
||||||
print("堆的数组表示:", heap);
|
""" Print a heap both in array and tree representations """
|
||||||
print("堆的树状表示:");
|
print("堆的数组表示:", heap)
|
||||||
root = list_to_tree(heap)
|
print("堆的树状表示:")
|
||||||
print_tree(root);
|
root: Optional[TreeNode] = list_to_tree(heap)
|
||||||
|
print_tree(root)
|
||||||
|
@ -34,8 +34,8 @@
|
|||||||
|
|
||||||
```python title="array.py"
|
```python title="array.py"
|
||||||
""" 初始化数组 """
|
""" 初始化数组 """
|
||||||
arr = [0] * 5 # [ 0, 0, 0, 0, 0 ]
|
arr: List[int] = [0] * 5 # [ 0, 0, 0, 0, 0 ]
|
||||||
nums = [1, 3, 2, 5, 4]
|
nums: List[int] = [1, 3, 2, 5, 4]
|
||||||
```
|
```
|
||||||
|
|
||||||
=== "Go"
|
=== "Go"
|
||||||
|
@ -37,9 +37,9 @@
|
|||||||
```python title=""
|
```python title=""
|
||||||
""" 链表结点类 """
|
""" 链表结点类 """
|
||||||
class ListNode:
|
class ListNode:
|
||||||
def __init__(self, x):
|
def __init__(self, val: int):
|
||||||
self.val = x # 结点值
|
self.val: int = val # 结点值
|
||||||
self.next = None # 指向下一结点的指针(引用)
|
self.next: Optional[ListNode] = None # 指向下一结点的指针(引用)
|
||||||
```
|
```
|
||||||
|
|
||||||
=== "Go"
|
=== "Go"
|
||||||
@ -609,10 +609,10 @@
|
|||||||
```python title=""
|
```python title=""
|
||||||
""" 双向链表结点类 """
|
""" 双向链表结点类 """
|
||||||
class ListNode:
|
class ListNode:
|
||||||
def __init__(self, x):
|
def __init__(self, val: int):
|
||||||
self.val = x # 结点值
|
self.val: int = val # 结点值
|
||||||
self.next = None # 指向后继结点的指针(引用)
|
self.next: Optional[ListNode] = None # 指向后继结点的指针(引用)
|
||||||
self.prev = None # 指向前驱结点的指针(引用)
|
self.prev: Optional[ListNode] = None # 指向前驱结点的指针(引用)
|
||||||
```
|
```
|
||||||
|
|
||||||
=== "Go"
|
=== "Go"
|
||||||
|
@ -35,9 +35,9 @@
|
|||||||
```python title="list.py"
|
```python title="list.py"
|
||||||
""" 初始化列表 """
|
""" 初始化列表 """
|
||||||
# 无初始值
|
# 无初始值
|
||||||
list1 = []
|
list1: List[int] = []
|
||||||
# 有初始值
|
# 有初始值
|
||||||
list = [1, 3, 2, 5, 4]
|
list: List[int] = [1, 3, 2, 5, 4]
|
||||||
```
|
```
|
||||||
|
|
||||||
=== "Go"
|
=== "Go"
|
||||||
@ -132,7 +132,7 @@
|
|||||||
|
|
||||||
```python title="list.py"
|
```python title="list.py"
|
||||||
""" 访问元素 """
|
""" 访问元素 """
|
||||||
num = list[1] # 访问索引 1 处的元素
|
num: int = list[1] # 访问索引 1 处的元素
|
||||||
|
|
||||||
""" 更新元素 """
|
""" 更新元素 """
|
||||||
list[1] = 0 # 将索引 1 处的元素更新为 0
|
list[1] = 0 # 将索引 1 处的元素更新为 0
|
||||||
@ -430,12 +430,12 @@
|
|||||||
|
|
||||||
```python title="list.py"
|
```python title="list.py"
|
||||||
""" 通过索引遍历列表 """
|
""" 通过索引遍历列表 """
|
||||||
count = 0
|
count: int = 0
|
||||||
for i in range(len(list)):
|
for i in range(len(list)):
|
||||||
count += 1
|
count += 1
|
||||||
|
|
||||||
""" 直接遍历列表元素 """
|
""" 直接遍历列表元素 """
|
||||||
count = 0
|
count: int = 0
|
||||||
for n in list:
|
for n in list:
|
||||||
count += 1
|
count += 1
|
||||||
```
|
```
|
||||||
@ -568,7 +568,7 @@
|
|||||||
|
|
||||||
```python title="list.py"
|
```python title="list.py"
|
||||||
""" 拼接两个列表 """
|
""" 拼接两个列表 """
|
||||||
list1 = [6, 8, 7, 10, 9]
|
list1: List[int] = [6, 8, 7, 10, 9]
|
||||||
list += list1 # 将列表 list1 拼接到 list 之后
|
list += list1 # 将列表 list1 拼接到 list 之后
|
||||||
```
|
```
|
||||||
|
|
||||||
|
@ -66,8 +66,8 @@
|
|||||||
int algorithm(int n) { // 输入数据
|
int algorithm(int n) { // 输入数据
|
||||||
const int a = 0; // 暂存数据(常量)
|
const int a = 0; // 暂存数据(常量)
|
||||||
int b = 0; // 暂存数据(变量)
|
int b = 0; // 暂存数据(变量)
|
||||||
Node* node = new Node(0); // 暂存数据(对象)
|
Node* node = new Node(0); // 暂存数据(对象)
|
||||||
int c = func(); // 栈帧空间(调用函数)
|
int c = func(); // 栈帧空间(调用函数)
|
||||||
return a + b + c; // 输出数据
|
return a + b + c; // 输出数据
|
||||||
}
|
}
|
||||||
```
|
```
|
||||||
@ -77,20 +77,20 @@
|
|||||||
```python title=""
|
```python title=""
|
||||||
""" 类 """
|
""" 类 """
|
||||||
class Node:
|
class Node:
|
||||||
def __init__(self, x):
|
def __init__(self, x: int):
|
||||||
self.val = x # 结点值
|
self.val: int = x # 结点值
|
||||||
self.next = None # 指向下一结点的指针(引用)
|
self.next: Optional[Node] = None # 指向下一结点的指针(引用)
|
||||||
|
|
||||||
""" 函数 """
|
""" 函数 """
|
||||||
def function():
|
def function() -> int:
|
||||||
# do something...
|
# do something...
|
||||||
return 0
|
return 0
|
||||||
|
|
||||||
def algorithm(n): # 输入数据
|
def algorithm(n) -> int: # 输入数据
|
||||||
b = 0 # 暂存数据(变量)
|
b: int = 0 # 暂存数据(变量)
|
||||||
node = Node(0) # 暂存数据(对象)
|
node = Node(0) # 暂存数据(对象)
|
||||||
c = function() # 栈帧空间(调用函数)
|
c: int = function() # 栈帧空间(调用函数)
|
||||||
return a + b + c # 输出数据
|
return a + b + c # 输出数据
|
||||||
```
|
```
|
||||||
|
|
||||||
=== "Go"
|
=== "Go"
|
||||||
@ -280,11 +280,11 @@
|
|||||||
=== "Python"
|
=== "Python"
|
||||||
|
|
||||||
```python title=""
|
```python title=""
|
||||||
def algorithm(n):
|
def algorithm(n: int) -> None:
|
||||||
a = 0 # O(1)
|
a: int = 0 # O(1)
|
||||||
b = [0] * 10000 # O(1)
|
b: List[int] = [0] * 10000 # O(1)
|
||||||
if n > 10:
|
if n > 10:
|
||||||
nums = [0] * n # O(n)
|
nums: List[int] = [0] * n # O(n)
|
||||||
```
|
```
|
||||||
|
|
||||||
=== "Go"
|
=== "Go"
|
||||||
@ -408,17 +408,17 @@
|
|||||||
=== "Python"
|
=== "Python"
|
||||||
|
|
||||||
```python title=""
|
```python title=""
|
||||||
def function():
|
def function() -> int:
|
||||||
# do something
|
# do something
|
||||||
return 0
|
return 0
|
||||||
|
|
||||||
""" 循环 O(1) """
|
""" 循环 O(1) """
|
||||||
def loop(n):
|
def loop(n: int) -> None:
|
||||||
for _ in range(n):
|
for _ in range(n):
|
||||||
function()
|
function()
|
||||||
|
|
||||||
""" 递归 O(n) """
|
""" 递归 O(n) """
|
||||||
def recur(n):
|
def recur(n: int) -> int:
|
||||||
if n == 1: return
|
if n == 1: return
|
||||||
return recur(n - 1)
|
return recur(n - 1)
|
||||||
```
|
```
|
||||||
|
@ -48,7 +48,7 @@ $$
|
|||||||
|
|
||||||
```python title=""
|
```python title=""
|
||||||
# 在某运行平台下
|
# 在某运行平台下
|
||||||
def algorithm(n):
|
def algorithm(n: int) -> None:
|
||||||
a = 2 # 1 ns
|
a = 2 # 1 ns
|
||||||
a = a + 1 # 1 ns
|
a = a + 1 # 1 ns
|
||||||
a = a * 2 # 10 ns
|
a = a * 2 # 10 ns
|
||||||
@ -213,14 +213,14 @@ $$
|
|||||||
|
|
||||||
```python title=""
|
```python title=""
|
||||||
# 算法 A 时间复杂度:常数阶
|
# 算法 A 时间复杂度:常数阶
|
||||||
def algorithm_A(n):
|
def algorithm_A(n: int) -> None:
|
||||||
print(0)
|
print(0)
|
||||||
# 算法 B 时间复杂度:线性阶
|
# 算法 B 时间复杂度:线性阶
|
||||||
def algorithm_B(n):
|
def algorithm_B(n: int) -> None:
|
||||||
for _ in range(n):
|
for _ in range(n):
|
||||||
print(0)
|
print(0)
|
||||||
# 算法 C 时间复杂度:常数阶
|
# 算法 C 时间复杂度:常数阶
|
||||||
def algorithm_C(n):
|
def algorithm_C(n: int) -> None:
|
||||||
for _ in range(1000000):
|
for _ in range(1000000):
|
||||||
print(0)
|
print(0)
|
||||||
```
|
```
|
||||||
@ -414,8 +414,8 @@ $$
|
|||||||
=== "Python"
|
=== "Python"
|
||||||
|
|
||||||
```python title=""
|
```python title=""
|
||||||
def algorithm(n):
|
def algorithm(n: int) -> None:
|
||||||
a = 1 # +1
|
a: int = 1 # +1
|
||||||
a = a + 1 # +1
|
a = a + 1 # +1
|
||||||
a = a * 2 # +1
|
a = a * 2 # +1
|
||||||
# 循环 n 次
|
# 循环 n 次
|
||||||
@ -605,9 +605,9 @@ $$
|
|||||||
=== "Python"
|
=== "Python"
|
||||||
|
|
||||||
```python title=""
|
```python title=""
|
||||||
def algorithm(n):
|
def algorithm(n: int) -> None:
|
||||||
a = 1 # +0(技巧 1)
|
a: int = 1 # +0(技巧 1)
|
||||||
a = a + n # +0(技巧 1)
|
a = a + n # +0(技巧 1)
|
||||||
# +n(技巧 2)
|
# +n(技巧 2)
|
||||||
for i in range(5 * n + 1):
|
for i in range(5 * n + 1):
|
||||||
print(0)
|
print(0)
|
||||||
|
@ -81,7 +81,7 @@
|
|||||||
|
|
||||||
```python title="hash_map.py"
|
```python title="hash_map.py"
|
||||||
""" 初始化哈希表 """
|
""" 初始化哈希表 """
|
||||||
mapp = {}
|
mapp: Dict = {}
|
||||||
|
|
||||||
""" 添加操作 """
|
""" 添加操作 """
|
||||||
# 在哈希表中添加键值对 (key, value)
|
# 在哈希表中添加键值对 (key, value)
|
||||||
@ -93,7 +93,7 @@
|
|||||||
|
|
||||||
""" 查询操作 """
|
""" 查询操作 """
|
||||||
# 向哈希表输入键 key ,得到值 value
|
# 向哈希表输入键 key ,得到值 value
|
||||||
name = mapp[15937]
|
name: str = mapp[15937]
|
||||||
|
|
||||||
""" 删除操作 """
|
""" 删除操作 """
|
||||||
# 在哈希表中删除键值对 (key, value)
|
# 在哈希表中删除键值对 (key, value)
|
||||||
|
@ -133,7 +133,7 @@
|
|||||||
heapq.heappush(max_heap, flag * 4)
|
heapq.heappush(max_heap, flag * 4)
|
||||||
|
|
||||||
""" 获取堆顶元素 """
|
""" 获取堆顶元素 """
|
||||||
peek = flag * max_heap[0] # 5
|
peek: int = flag * max_heap[0] # 5
|
||||||
|
|
||||||
""" 堆顶元素出堆 """
|
""" 堆顶元素出堆 """
|
||||||
# 出堆元素会形成一个从大到小的序列
|
# 出堆元素会形成一个从大到小的序列
|
||||||
@ -144,13 +144,13 @@
|
|||||||
val = flag * heapq.heappop(max_heap) # 1
|
val = flag * heapq.heappop(max_heap) # 1
|
||||||
|
|
||||||
""" 获取堆大小 """
|
""" 获取堆大小 """
|
||||||
size = len(max_heap)
|
size: int = len(max_heap)
|
||||||
|
|
||||||
""" 判断堆是否为空 """
|
""" 判断堆是否为空 """
|
||||||
is_empty = not max_heap
|
is_empty: bool = not max_heap
|
||||||
|
|
||||||
""" 输入列表并建堆 """
|
""" 输入列表并建堆 """
|
||||||
min_heap = [1, 3, 2, 5, 4]
|
min_heap: List[int] = [1, 3, 2, 5, 4]
|
||||||
heapq.heapify(min_heap)
|
heapq.heapify(min_heap)
|
||||||
```
|
```
|
||||||
|
|
||||||
|
@ -64,43 +64,9 @@
|
|||||||
=== "C++"
|
=== "C++"
|
||||||
|
|
||||||
```cpp title="merge_sort.cpp"
|
```cpp title="merge_sort.cpp"
|
||||||
/* 合并左子数组和右子数组 */
|
[class]{}-[func]{merge}
|
||||||
// 左子数组区间 [left, mid]
|
|
||||||
// 右子数组区间 [mid + 1, right]
|
|
||||||
void merge(vector<int>& nums, int left, int mid, int right) {
|
|
||||||
// 初始化辅助数组
|
|
||||||
vector<int> tmp(nums.begin() + left, nums.begin() + right + 1);
|
|
||||||
// 左子数组的起始索引和结束索引
|
|
||||||
int leftStart = left - left, leftEnd = mid - left;
|
|
||||||
// 右子数组的起始索引和结束索引
|
|
||||||
int rightStart = mid + 1 - left, rightEnd = right - left;
|
|
||||||
// i, j 分别指向左子数组、右子数组的首元素
|
|
||||||
int i = leftStart, j = rightStart;
|
|
||||||
// 通过覆盖原数组 nums 来合并左子数组和右子数组
|
|
||||||
for (int k = left; k <= right; k++) {
|
|
||||||
// 若“左子数组已全部合并完”,则选取右子数组元素,并且 j++
|
|
||||||
if (i > leftEnd)
|
|
||||||
nums[k] = tmp[j++];
|
|
||||||
// 否则,若“右子数组已全部合并完”或“左子数组元素 <= 右子数组元素”,则选取左子数组元素,并且 i++
|
|
||||||
else if (j > rightEnd || tmp[i] <= tmp[j])
|
|
||||||
nums[k] = tmp[i++];
|
|
||||||
// 否则,若“左右子数组都未全部合并完”且“左子数组元素 > 右子数组元素”,则选取右子数组元素,并且 j++
|
|
||||||
else
|
|
||||||
nums[k] = tmp[j++];
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
/* 归并排序 */
|
[class]{}-[func]{mergeSort}
|
||||||
void mergeSort(vector<int>& nums, int left, int right) {
|
|
||||||
// 终止条件
|
|
||||||
if (left >= right) return; // 当子数组长度为 1 时终止递归
|
|
||||||
// 划分阶段
|
|
||||||
int mid = (left + right) / 2; // 计算中点
|
|
||||||
mergeSort(nums, left, mid); // 递归左子数组
|
|
||||||
mergeSort(nums, mid + 1, right); // 递归右子数组
|
|
||||||
// 合并阶段
|
|
||||||
merge(nums, left, mid, right);
|
|
||||||
}
|
|
||||||
```
|
```
|
||||||
|
|
||||||
=== "Python"
|
=== "Python"
|
||||||
@ -114,139 +80,25 @@
|
|||||||
=== "Go"
|
=== "Go"
|
||||||
|
|
||||||
```go title="merge_sort.go"
|
```go title="merge_sort.go"
|
||||||
/*
|
[class]{}-[func]{merge}
|
||||||
合并左子数组和右子数组
|
|
||||||
左子数组区间 [left, mid]
|
|
||||||
右子数组区间 [mid + 1, right]
|
|
||||||
*/
|
|
||||||
func merge(nums []int, left, mid, right int) {
|
|
||||||
// 初始化辅助数组 借助 copy 模块
|
|
||||||
tmp := make([]int, right-left+1)
|
|
||||||
for i := left; i <= right; i++ {
|
|
||||||
tmp[i-left] = nums[i]
|
|
||||||
}
|
|
||||||
// 左子数组的起始索引和结束索引
|
|
||||||
leftStart, leftEnd := left-left, mid-left
|
|
||||||
// 右子数组的起始索引和结束索引
|
|
||||||
rightStart, rightEnd := mid+1-left, right-left
|
|
||||||
// i, j 分别指向左子数组、右子数组的首元素
|
|
||||||
i, j := leftStart, rightStart
|
|
||||||
// 通过覆盖原数组 nums 来合并左子数组和右子数组
|
|
||||||
for k := left; k <= right; k++ {
|
|
||||||
// 若“左子数组已全部合并完”,则选取右子数组元素,并且 j++
|
|
||||||
if i > leftEnd {
|
|
||||||
nums[k] = tmp[j]
|
|
||||||
j++
|
|
||||||
// 否则,若“右子数组已全部合并完”或“左子数组元素 <= 右子数组元素”,则选取左子数组元素,并且 i++
|
|
||||||
} else if j > rightEnd || tmp[i] <= tmp[j] {
|
|
||||||
nums[k] = tmp[i]
|
|
||||||
i++
|
|
||||||
// 否则,若“左右子数组都未全部合并完”且“左子数组元素 > 右子数组元素”,则选取右子数组元素,并且 j++
|
|
||||||
} else {
|
|
||||||
nums[k] = tmp[j]
|
|
||||||
j++
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
func mergeSort(nums []int, left, right int) {
|
[class]{}-[func]{mergeSort}
|
||||||
// 终止条件
|
|
||||||
if left >= right {
|
|
||||||
return
|
|
||||||
}
|
|
||||||
// 划分阶段
|
|
||||||
mid := (left + right) / 2
|
|
||||||
mergeSort(nums, left, mid)
|
|
||||||
mergeSort(nums, mid+1, right)
|
|
||||||
// 合并阶段
|
|
||||||
merge(nums, left, mid, right)
|
|
||||||
}
|
|
||||||
```
|
```
|
||||||
|
|
||||||
=== "JavaScript"
|
=== "JavaScript"
|
||||||
|
|
||||||
```javascript title="merge_sort.js"
|
```javascript title="merge_sort.js"
|
||||||
/* 合并左子数组和右子数组 */
|
[class]{}-[func]{merge}
|
||||||
// 左子数组区间 [left, mid]
|
|
||||||
// 右子数组区间 [mid + 1, right]
|
[class]{}-[func]{mergeSort}
|
||||||
function merge(nums, left, mid, right) {
|
|
||||||
// 初始化辅助数组
|
|
||||||
let tmp = nums.slice(left, right + 1);
|
|
||||||
// 左子数组的起始索引和结束索引
|
|
||||||
let leftStart = left - left, leftEnd = mid - left;
|
|
||||||
// 右子数组的起始索引和结束索引
|
|
||||||
let rightStart = mid + 1 - left, rightEnd = right - left;
|
|
||||||
// i, j 分别指向左子数组、右子数组的首元素
|
|
||||||
let i = leftStart, j = rightStart;
|
|
||||||
// 通过覆盖原数组 nums 来合并左子数组和右子数组
|
|
||||||
for (let k = left; k <= right; k++) {
|
|
||||||
// 若“左子数组已全部合并完”,则选取右子数组元素,并且 j++
|
|
||||||
if (i > leftEnd) {
|
|
||||||
nums[k] = tmp[j++];
|
|
||||||
// 否则,若“右子数组已全部合并完”或“左子数组元素 <= 右子数组元素”,则选取左子数组元素,并且 i++
|
|
||||||
} else if (j > rightEnd || tmp[i] <= tmp[j]) {
|
|
||||||
nums[k] = tmp[i++];
|
|
||||||
// 否则,若“左右子数组都未全部合并完”且“左子数组元素 > 右子数组元素”,则选取右子数组元素,并且 j++
|
|
||||||
} else {
|
|
||||||
nums[k] = tmp[j++];
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
/* 归并排序 */
|
|
||||||
function mergeSort(nums, left, right) {
|
|
||||||
// 终止条件
|
|
||||||
if (left >= right) return; // 当子数组长度为 1 时终止递归
|
|
||||||
// 划分阶段
|
|
||||||
let mid = Math.floor((left + right) / 2); // 计算中点
|
|
||||||
mergeSort(nums, left, mid); // 递归左子数组
|
|
||||||
mergeSort(nums, mid + 1, right); // 递归右子数组
|
|
||||||
// 合并阶段
|
|
||||||
merge(nums, left, mid, right);
|
|
||||||
}
|
|
||||||
```
|
```
|
||||||
|
|
||||||
=== "TypeScript"
|
=== "TypeScript"
|
||||||
|
|
||||||
```typescript title="merge_sort.ts"
|
```typescript title="merge_sort.ts"
|
||||||
/* 合并左子数组和右子数组 */
|
[class]{}-[func]{merge}
|
||||||
// 左子数组区间 [left, mid]
|
|
||||||
// 右子数组区间 [mid + 1, right]
|
|
||||||
function merge(nums: number[], left: number, mid: number, right: number): void {
|
|
||||||
// 初始化辅助数组
|
|
||||||
let tmp = nums.slice(left, right + 1);
|
|
||||||
// 左子数组的起始索引和结束索引
|
|
||||||
let leftStart = left - left, leftEnd = mid - left;
|
|
||||||
// 右子数组的起始索引和结束索引
|
|
||||||
let rightStart = mid + 1 - left, rightEnd = right - left;
|
|
||||||
// i, j 分别指向左子数组、右子数组的首元素
|
|
||||||
let i = leftStart, j = rightStart;
|
|
||||||
// 通过覆盖原数组 nums 来合并左子数组和右子数组
|
|
||||||
for (let k = left; k <= right; k++) {
|
|
||||||
// 若“左子数组已全部合并完”,则选取右子数组元素,并且 j++
|
|
||||||
if (i > leftEnd) {
|
|
||||||
nums[k] = tmp[j++];
|
|
||||||
// 否则,若“右子数组已全部合并完”或“左子数组元素 <= 右子数组元素”,则选取左子数组元素,并且 i++
|
|
||||||
} else if (j > rightEnd || tmp[i] <= tmp[j]) {
|
|
||||||
nums[k] = tmp[i++];
|
|
||||||
// 否则,若“左右子数组都未全部合并完”且“左子数组元素 > 右子数组元素”,则选取右子数组元素,并且 j++
|
|
||||||
} else {
|
|
||||||
nums[k] = tmp[j++];
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
/* 归并排序 */
|
[class]{}-[func]{mergeSort}
|
||||||
function mergeSort(nums: number[], left: number, right: number): void {
|
|
||||||
// 终止条件
|
|
||||||
if (left >= right) return; // 当子数组长度为 1 时终止递归
|
|
||||||
// 划分阶段
|
|
||||||
let mid = Math.floor((left + right) / 2); // 计算中点
|
|
||||||
mergeSort(nums, left, mid); // 递归左子数组
|
|
||||||
mergeSort(nums, mid + 1, right); // 递归右子数组
|
|
||||||
// 合并阶段
|
|
||||||
merge(nums, left, mid, right);
|
|
||||||
}
|
|
||||||
```
|
```
|
||||||
|
|
||||||
=== "C"
|
=== "C"
|
||||||
@ -266,62 +118,17 @@
|
|||||||
=== "Swift"
|
=== "Swift"
|
||||||
|
|
||||||
```swift title="merge_sort.swift"
|
```swift title="merge_sort.swift"
|
||||||
/**
|
[class]{}-[func]{merge}
|
||||||
* 合并左子数组和右子数组
|
|
||||||
* 左子数组区间 [left, mid]
|
|
||||||
* 右子数组区间 [mid + 1, right]
|
|
||||||
*/
|
|
||||||
func merge(nums: inout [Int], left: Int, mid: Int, right: Int) {
|
|
||||||
// 初始化辅助数组
|
|
||||||
let tmp = Array(nums[left ..< (right + 1)])
|
|
||||||
// 左子数组的起始索引和结束索引
|
|
||||||
let leftStart = left - left
|
|
||||||
let leftEnd = mid - left
|
|
||||||
// 右子数组的起始索引和结束索引
|
|
||||||
let rightStart = mid + 1 - left
|
|
||||||
let rightEnd = right - left
|
|
||||||
// i, j 分别指向左子数组、右子数组的首元素
|
|
||||||
var i = leftStart
|
|
||||||
var j = rightStart
|
|
||||||
// 通过覆盖原数组 nums 来合并左子数组和右子数组
|
|
||||||
for k in left ... right {
|
|
||||||
// 若“左子数组已全部合并完”,则选取右子数组元素,并且 j++
|
|
||||||
if i > leftEnd {
|
|
||||||
nums[k] = tmp[j]
|
|
||||||
j += 1
|
|
||||||
}
|
|
||||||
// 否则,若“右子数组已全部合并完”或“左子数组元素 <= 右子数组元素”,则选取左子数组元素,并且 i++
|
|
||||||
else if j > rightEnd || tmp[i] <= tmp[j] {
|
|
||||||
nums[k] = tmp[i]
|
|
||||||
i += 1
|
|
||||||
}
|
|
||||||
// 否则,若“左右子数组都未全部合并完”且“左子数组元素 > 右子数组元素”,则选取右子数组元素,并且 j++
|
|
||||||
else {
|
|
||||||
nums[k] = tmp[j]
|
|
||||||
j += 1
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
/* 归并排序 */
|
[class]{}-[func]{mergeSort}
|
||||||
func mergeSort(nums: inout [Int], left: Int, right: Int) {
|
|
||||||
// 终止条件
|
|
||||||
if left >= right { // 当子数组长度为 1 时终止递归
|
|
||||||
return
|
|
||||||
}
|
|
||||||
// 划分阶段
|
|
||||||
let mid = (left + right) / 2 // 计算中点
|
|
||||||
mergeSort(nums: &nums, left: left, right: mid) // 递归左子数组
|
|
||||||
mergeSort(nums: &nums, left: mid + 1, right: right) // 递归右子数组
|
|
||||||
// 合并阶段
|
|
||||||
merge(nums: &nums, left: left, mid: mid, right: right)
|
|
||||||
}
|
|
||||||
```
|
```
|
||||||
|
|
||||||
=== "Zig"
|
=== "Zig"
|
||||||
|
|
||||||
```zig title="merge_sort.zig"
|
```zig title="merge_sort.zig"
|
||||||
|
[class]{}-[func]{merge}
|
||||||
|
|
||||||
|
[class]{}-[func]{mergeSort}
|
||||||
```
|
```
|
||||||
|
|
||||||
下面重点解释一下合并方法 `merge()` 的流程:
|
下面重点解释一下合并方法 `merge()` 的流程:
|
||||||
|
@ -83,7 +83,7 @@
|
|||||||
|
|
||||||
```python title="deque.py"
|
```python title="deque.py"
|
||||||
""" 初始化双向队列 """
|
""" 初始化双向队列 """
|
||||||
deque = deque()
|
deque: Deque[int] = collections.deque()
|
||||||
|
|
||||||
""" 元素入队 """
|
""" 元素入队 """
|
||||||
deque.append(2) # 添加至队尾
|
deque.append(2) # 添加至队尾
|
||||||
@ -93,18 +93,18 @@
|
|||||||
deque.appendleft(1)
|
deque.appendleft(1)
|
||||||
|
|
||||||
""" 访问元素 """
|
""" 访问元素 """
|
||||||
front = deque[0] # 队首元素
|
front: int = deque[0] # 队首元素
|
||||||
rear = deque[-1] # 队尾元素
|
rear: int = deque[-1] # 队尾元素
|
||||||
|
|
||||||
""" 元素出队 """
|
""" 元素出队 """
|
||||||
pop_front = deque.popleft() # 队首元素出队
|
pop_front: int = deque.popleft() # 队首元素出队
|
||||||
pop_rear = deque.pop() # 队尾元素出队
|
pop_rear: int = deque.pop() # 队尾元素出队
|
||||||
|
|
||||||
""" 获取双向队列的长度 """
|
""" 获取双向队列的长度 """
|
||||||
size = len(deque)
|
size: int = len(deque)
|
||||||
|
|
||||||
""" 判断双向队列是否为空 """
|
""" 判断双向队列是否为空 """
|
||||||
is_empty = len(deque) == 0
|
is_empty: bool = len(deque) == 0
|
||||||
```
|
```
|
||||||
|
|
||||||
=== "Go"
|
=== "Go"
|
||||||
|
@ -80,7 +80,7 @@
|
|||||||
""" 初始化队列 """
|
""" 初始化队列 """
|
||||||
# 在 Python 中,我们一般将双向队列类 deque 看作队列使用
|
# 在 Python 中,我们一般将双向队列类 deque 看作队列使用
|
||||||
# 虽然 queue.Queue() 是纯正的队列类,但不太好用,因此不建议
|
# 虽然 queue.Queue() 是纯正的队列类,但不太好用,因此不建议
|
||||||
que = collections.deque()
|
que: Deque[int] = collections.deque()
|
||||||
|
|
||||||
""" 元素入队 """
|
""" 元素入队 """
|
||||||
que.append(1)
|
que.append(1)
|
||||||
@ -90,16 +90,16 @@
|
|||||||
que.append(4)
|
que.append(4)
|
||||||
|
|
||||||
""" 访问队首元素 """
|
""" 访问队首元素 """
|
||||||
front = que[0];
|
front: int = que[0];
|
||||||
|
|
||||||
""" 元素出队 """
|
""" 元素出队 """
|
||||||
pop = que.popleft()
|
pop: int = que.popleft()
|
||||||
|
|
||||||
""" 获取队列的长度 """
|
""" 获取队列的长度 """
|
||||||
size = len(que)
|
size: int = len(que)
|
||||||
|
|
||||||
""" 判断队列是否为空 """
|
""" 判断队列是否为空 """
|
||||||
is_empty = len(que) == 0
|
is_empty: bool = len(que) == 0
|
||||||
```
|
```
|
||||||
|
|
||||||
=== "Go"
|
=== "Go"
|
||||||
|
@ -81,7 +81,7 @@
|
|||||||
```python title="stack.py"
|
```python title="stack.py"
|
||||||
""" 初始化栈 """
|
""" 初始化栈 """
|
||||||
# Python 没有内置的栈类,可以把 List 当作栈来使用
|
# Python 没有内置的栈类,可以把 List 当作栈来使用
|
||||||
stack = []
|
stack: List[int] = []
|
||||||
|
|
||||||
""" 元素入栈 """
|
""" 元素入栈 """
|
||||||
stack.append(1)
|
stack.append(1)
|
||||||
@ -91,16 +91,16 @@
|
|||||||
stack.append(4)
|
stack.append(4)
|
||||||
|
|
||||||
""" 访问栈顶元素 """
|
""" 访问栈顶元素 """
|
||||||
peek = stack[-1]
|
peek: int = stack[-1]
|
||||||
|
|
||||||
""" 元素出栈 """
|
""" 元素出栈 """
|
||||||
pop = stack.pop()
|
pop: int = stack.pop()
|
||||||
|
|
||||||
""" 获取栈的长度 """
|
""" 获取栈的长度 """
|
||||||
size = len(stack)
|
size: int = len(stack)
|
||||||
|
|
||||||
""" 判断是否为空 """
|
""" 判断是否为空 """
|
||||||
is_empty = len(stack) == 0
|
is_empty: bool = len(stack) == 0
|
||||||
```
|
```
|
||||||
|
|
||||||
=== "Go"
|
=== "Go"
|
||||||
|
@ -27,9 +27,9 @@ G. M. Adelson-Velsky 和 E. M. Landis 在其 1962 年发表的论文 "An algorit
|
|||||||
```java title=""
|
```java title=""
|
||||||
/* AVL 树结点类 */
|
/* AVL 树结点类 */
|
||||||
class TreeNode {
|
class TreeNode {
|
||||||
public int val; // 结点值
|
public int val; // 结点值
|
||||||
public int height; // 结点高度
|
public int height; // 结点高度
|
||||||
public TreeNode left; // 左子结点
|
public TreeNode left; // 左子结点
|
||||||
public TreeNode right; // 右子结点
|
public TreeNode right; // 右子结点
|
||||||
public TreeNode(int x) { val = x; }
|
public TreeNode(int x) { val = x; }
|
||||||
}
|
}
|
||||||
@ -40,10 +40,10 @@ G. M. Adelson-Velsky 和 E. M. Landis 在其 1962 年发表的论文 "An algorit
|
|||||||
```cpp title=""
|
```cpp title=""
|
||||||
/* AVL 树结点类 */
|
/* AVL 树结点类 */
|
||||||
struct TreeNode {
|
struct TreeNode {
|
||||||
int val{}; // 结点值
|
int val{}; // 结点值
|
||||||
int height = 0; // 结点高度
|
int height = 0; // 结点高度
|
||||||
TreeNode *left{}; // 左子结点
|
TreeNode *left{}; // 左子结点
|
||||||
TreeNode *right{}; // 右子结点
|
TreeNode *right{}; // 右子结点
|
||||||
TreeNode() = default;
|
TreeNode() = default;
|
||||||
explicit TreeNode(int x) : val(x){}
|
explicit TreeNode(int x) : val(x){}
|
||||||
};
|
};
|
||||||
@ -54,11 +54,11 @@ G. M. Adelson-Velsky 和 E. M. Landis 在其 1962 年发表的论文 "An algorit
|
|||||||
```python title=""
|
```python title=""
|
||||||
""" AVL 树结点类 """
|
""" AVL 树结点类 """
|
||||||
class TreeNode:
|
class TreeNode:
|
||||||
def __init__(self, val=None, left=None, right=None):
|
def __init__(self, val: int):
|
||||||
self.val = val # 结点值
|
self.val: int = val # 结点值
|
||||||
self.height = 0 # 结点高度
|
self.height: int = 0 # 结点高度
|
||||||
self.left = left # 左子结点引用
|
self.left: Optional[TreeNode] = None # 左子结点引用
|
||||||
self.right = right # 右子结点引用
|
self.right: Optional[TreeNode] = None # 右子结点引用
|
||||||
```
|
```
|
||||||
|
|
||||||
=== "Go"
|
=== "Go"
|
||||||
|
@ -5,7 +5,7 @@
|
|||||||
=== "Java"
|
=== "Java"
|
||||||
|
|
||||||
```java title=""
|
```java title=""
|
||||||
/* 链表结点类 */
|
/* 二叉树结点类 */
|
||||||
class TreeNode {
|
class TreeNode {
|
||||||
int val; // 结点值
|
int val; // 结点值
|
||||||
TreeNode left; // 左子结点指针
|
TreeNode left; // 左子结点指针
|
||||||
@ -17,7 +17,7 @@
|
|||||||
=== "C++"
|
=== "C++"
|
||||||
|
|
||||||
```cpp title=""
|
```cpp title=""
|
||||||
/* 链表结点结构体 */
|
/* 二叉树结点结构体 */
|
||||||
struct TreeNode {
|
struct TreeNode {
|
||||||
int val; // 结点值
|
int val; // 结点值
|
||||||
TreeNode *left; // 左子结点指针
|
TreeNode *left; // 左子结点指针
|
||||||
@ -29,18 +29,18 @@
|
|||||||
=== "Python"
|
=== "Python"
|
||||||
|
|
||||||
```python title=""
|
```python title=""
|
||||||
""" 链表结点类 """
|
""" 二叉树结点类 """
|
||||||
class TreeNode:
|
class TreeNode:
|
||||||
def __init__(self, val=None, left=None, right=None):
|
def __init__(self, val: int):
|
||||||
self.val = val # 结点值
|
self.val: int = val # 结点值
|
||||||
self.left = left # 左子结点指针
|
self.left: Optional[TreeNode] = None # 左子结点指针
|
||||||
self.right = right # 右子结点指针
|
self.right: Optional[TreeNode] = None # 右子结点指针
|
||||||
```
|
```
|
||||||
|
|
||||||
=== "Go"
|
=== "Go"
|
||||||
|
|
||||||
```go title=""
|
```go title=""
|
||||||
/* 链表结点结构体 */
|
/* 二叉树结点结构体 */
|
||||||
type TreeNode struct {
|
type TreeNode struct {
|
||||||
Val int
|
Val int
|
||||||
Left *TreeNode
|
Left *TreeNode
|
||||||
@ -59,7 +59,7 @@
|
|||||||
=== "JavaScript"
|
=== "JavaScript"
|
||||||
|
|
||||||
```javascript title=""
|
```javascript title=""
|
||||||
/* 链表结点类 */
|
/* 二叉树结点类 */
|
||||||
function TreeNode(val, left, right) {
|
function TreeNode(val, left, right) {
|
||||||
this.val = (val === undefined ? 0 : val); // 结点值
|
this.val = (val === undefined ? 0 : val); // 结点值
|
||||||
this.left = (left === undefined ? null : left); // 左子结点指针
|
this.left = (left === undefined ? null : left); // 左子结点指针
|
||||||
@ -70,7 +70,7 @@
|
|||||||
=== "TypeScript"
|
=== "TypeScript"
|
||||||
|
|
||||||
```typescript title=""
|
```typescript title=""
|
||||||
/* 链表结点类 */
|
/* 二叉树结点类 */
|
||||||
class TreeNode {
|
class TreeNode {
|
||||||
val: number;
|
val: number;
|
||||||
left: TreeNode | null;
|
left: TreeNode | null;
|
||||||
@ -93,7 +93,7 @@
|
|||||||
=== "C#"
|
=== "C#"
|
||||||
|
|
||||||
```csharp title=""
|
```csharp title=""
|
||||||
/* 链表结点类 */
|
/* 二叉树结点类 */
|
||||||
class TreeNode {
|
class TreeNode {
|
||||||
int val; // 结点值
|
int val; // 结点值
|
||||||
TreeNode? left; // 左子结点指针
|
TreeNode? left; // 左子结点指针
|
||||||
@ -105,7 +105,7 @@
|
|||||||
=== "Swift"
|
=== "Swift"
|
||||||
|
|
||||||
```swift title=""
|
```swift title=""
|
||||||
/* 链表结点类 */
|
/* 二叉树结点类 */
|
||||||
class TreeNode {
|
class TreeNode {
|
||||||
var val: Int // 结点值
|
var val: Int // 结点值
|
||||||
var left: TreeNode? // 左子结点指针
|
var left: TreeNode? // 左子结点指针
|
||||||
|
Loading…
x
Reference in New Issue
Block a user