列表是动态存储的,长度大小不固定,可以随意地增加、删减或者改变元素
元组是静态存储的,无法增删改,想要对已有的元组做任何“改变”,就只能开辟一块内存,创建新的元组
Note:
数组与列表有两点不同:
Note:
一般使用列表结构就可以实现栈
class Stack:
def __init__(self):
self.stack = []
def push(self, val):
self.stack.append(val)
def pop(self):
return self.stack.pop()
def get_top(self):
if len(self.stack) > 0:
return self.stack[-1]
else:
return None
stack = Stack()
stack.push(1)
stack.push(2)
print(stack.pop())
栈的应用:括号匹配问题
class Stack:
def __init__(self):
self.stack = []
def push(self, val):
self.stack.append(val)
def pop(self):
return self.stack.pop()
def get_top(self):
if len(self.stack) > 0:
return self.stack[-1]
else:
return None
def is_empty(self):
return len(self.stack) == 0
def brace_match(string):
match = {')': '(', '}': '{', ']': '['} # 键值对
stack = Stack()
for i in string:
if i in {'(', '{', '['}:
stack.push(i)
else:
if stack.is_empty():
return False
elif stack.get_top() == match[i]:
stack.pop()
else:
return False
if stack.is_empty():
return True
else:
return False
print(brace_match('[{()}]'))
队列的实现方式:环形队列
Note:
总结:
class Queue:
def __init__(self, size=100):
self.queue = [0 for _ in range(100)]
self.size = size
self.rear = 0 # 队尾
self.front = 0 # 队首
def push(self, element):
'''入队'''
if not self.is_filled():
self.rear = (self.rear + 1) % self.size
self.queue[self.rear] = element
else:
raise IndexError("Queue is filled!")
def pop(self):
'''出队'''
if not self.is_empty():
self.front = (self.front + 1) % self.size
return self.queue[self.front]
else:
raise IndexError('Queue is empty!')
def is_empty(self):
'''判断队空'''
return self.rear == self.front
def is_filled(self):
'''判断队满'''
return self.front == (self.rear + 1) % self.size
q = Queue(size=5)
for i in range(4): # 0,1,2,3 ; size=5 是因为判断队满的时候留了一个空位置
q.push(i)
print(q.is_filled())
内置模块
# 内置模块
# collections 为结构包
from collections import deque
q = deque([1, 2, 3, 4, 5], 5)
# 单向队列
q.append(6) # 队尾进队
print(q.popleft()) # 队首出队
# 双向队列
q.appendleft(1) # 队首进队
print(q.popleft()) # 队首出队
q.append(2) # 队尾入队
print(q.pop()) # 队尾出队
结果:
2
1
2
Process finished with exit code 0
Note:
应用:
如上面Note说的,如果size满了,会自动将前面的元素弹出,那么应用在哪里呢?
例如:我们先创建一个test文件,希望可以输出后面几行的内容该怎么做?
代码如下:
def tail(n):
with open('Queue2_test.txt', 'r') as f:
q = deque(f, n)
return q
print((tail(5)))
结果如下:
deque(['sbdujaodf\n', 'bsjcb\n', 'sda\n', 'cvxcvg\n', 'asd\n'], maxlen=5)
Process finished with exit code 0
这样,就使用队列完成了对文本后面几行的输出。
# 迷宫问题
maze = [
[1, 1, 1, 1, 1, 1, 1, 1, 1, 1],
[1, 0, 0, 1, 0, 0, 0, 1, 0, 1],
[1, 0, 0, 1, 0, 0, 0, 1, 0, 1],
[1, 0, 0, 0, 0, 1, 1, 0, 0, 1],
[1, 0, 1, 1, 1, 0, 0, 0, 0, 1],
[1, 0, 0, 0, 0, 0, 0, 0, 0, 1],
[1, 0, 1, 1, 1, 0, 1, 1, 0, 1],
[1, 0, 1, 1, 1, 0, 1, 1, 0, 1],
[1, 1, 0, 0, 0, 0, 0, 0, 0, 1],
[1, 1, 1, 1, 1, 1, 1, 1, 1, 1]
]
# 新列表存储四个方向
dirs = [
lambda x, y: (x + 1, y),
lambda x, y: (x - 1, y),
lambda x, y: (x, y + 1),
lambda x, y: (x, y - 1)
]
def maze_path(x1, y1, x2, y2):
'''
:param x1: 起点坐标
:param y1:
:param x2: 终点坐标
:param y2:
'''
stack = []
stack.append((x1, y1))
# 栈空表示没有通路
while (len(stack) > 0):
# 当前节点 curNode
curNode = stack[-1]
if curNode[0] == x2 and curNode[1] == y2:
# 走到终点
for p in stack:
print(p)
return True
# 上(x-1) 下(x+1) 左(y-1) 右(y+1)四个方向
for dir in dirs:
# 下一个节点
nextNode = dir(curNode[0], curNode[1])
# 如果下一个节点能走
if maze[[nextNode[0]][nextNode[1]]] == 0:
stack.append(nextNode)
maze[nextNode[0]][nextNode[1]] = 2 # 标记为已经走过了
break
# 一个都找不到
else:
maze[nextNode[0]][nextNode[1]] = 2
stack.pop()
else:
print('None path')
return False
maze_path(1, 1, 8, 8)
from collections import deque
# 迷宫问题
maze = [
[1, 1, 1, 1, 1, 1, 1, 1, 1, 1],
[1, 0, 0, 1, 0, 0, 0, 1, 0, 1],
[1, 0, 0, 1, 0, 0, 0, 1, 0, 1],
[1, 0, 0, 0, 0, 1, 1, 0, 0, 1],
[1, 0, 1, 1, 1, 0, 0, 0, 0, 1],
[1, 0, 0, 0, 0, 0, 0, 0, 0, 1],
[1, 0, 1, 1, 1, 0, 1, 1, 0, 1],
[1, 0, 1, 1, 1, 0, 1, 1, 0, 1],
[1, 1, 0, 0, 0, 0, 0, 0, 0, 1],
[1, 1, 1, 1, 1, 1, 1, 1, 1, 1]
]
# 新列表存储四个方向
dirs = [
lambda x, y: (x + 1, y),
lambda x, y: (x - 1, y),
lambda x, y: (x, y + 1),
lambda x, y: (x, y - 1)
]
def print_r(path):
curNode = path[-1]
realpath = []
while curNode[2] != -1:
realpath.append(curNode[0], curNode[1])
curNode = curNode[2]
# 起点
realpath.append(curNode[0:2])
realpath.reverse()
for node in realpath:
print(node)
def maze_path_queue(x1, y1, x2, y2):
queue = deque()
queue.append((x1, y1, -1))
# path用于存储出队节点,方便后面查找路径
path = []
while len(queue) > 0:
curNode = queue.popleft()
path.append(curNode)
if curNode[0] == x2 and curNode[1] == y2:
# 终点
print_r(path)
return True
for dir in dirs:
# 搜索当前节点周围节点
nextNode = dir(curNode[0], curNode[1])
if maze[nextNode[0]][nextNode[1]] == 0:
queue.append(nextNode[0], nextNode[1], len(path) - 1)
maze[nextNode[0]][nextNode[1]] = 2 # 标记已经走过
else:
return False
maze_path_queue(1, 1, 8, 8)
头插法
# 链表
class Node:
def __init__(self, item):
self.item = item
self.next = None
def creat_linklist(li):
head = Node(li[0])
for i in li[1:]:
'''头插法'''
node = Node(i)
node.next = head
head = node
return head
def print_link_list(li):
while li:
print(li.item, end=',')
li = li.next
li = creat_linklist([1, 2, 3, 4])
print_link_list(li)
尾插法
# 链表
class Node:
def __init__(self, item):
self.item = item
self.next = None
def creat_linklist_head(li):
head = Node(li[0])
for i in li[1:]:
'''头插法'''
node = Node(i)
node.next = head
head = node
return head
def print_link_list(li):
while li:
print(li.item, end=',')
li = li.next
def creat_linklist_tail(li):
head = Node(li[0])
tail = head
for i in li[1:]:
node = Node(i)
tail.next = node
tail = node
return head
# li = creat_linklist_head([1, 2, 3, 4])
li1 = creat_linklist_tail([1, 2, 3, 4])
# print_link_list(li)
print_link_list(li1)
插入
删除
插入
删除