队列是一种特殊的线性表,只允许在队列尾部进行元组插入操作和在队列头部进行元素删除操作,具有“先入先出(FIFO)”或“后入后出(LILO)”的特点,在多线程编程、作业管理等方面有重要应用。
Python列表对象的append()方法用于在列表尾部追加元素,pop(0)可以删除并返回列表头部的元素。
1 >>> x = []
2 >>>
3 >>> #在列表尾部追加元素,模拟入队操作
4 >>> x.append(1)
5 >>> x.append(2)
6 >>> x.append(3)
7 >>> x
8 [1, 2, 3]
9 >>>
10 >>> #在头部弹出元素,模拟出队操作
11 >>> x.pop(0)
12 1
13 >>> x
14 [2, 3]
15 >>> x.pop(0)
16 2
17 >>> x.pop(0)
18 3
19 >>> x
20 []
21 >>> x.pop(0)
22 Traceback (most recent call last):
23 File "<pyshell#14>", line 1, in <module>
24 x.pop(0)
25 IndexError: pop from empty list
26 >>>
从上面的代码可以看出,使用Python列表直接模拟队列结构,无法限制队列的大小,并且当列表为空时进行弹出元素的操作会抛出异常。可以对列表进行封装,自定义队列来避免这些问题。
设计自定义队列,模拟入队、出队等基本操作。
1 class myQueue:
2 #构造函数,默认队列大小为10
3 def __init__(self,size = 10):
4 self._content = []
5 self._size = size
6 self._current = 0
7
8 #析构函数
9 def __del__(self):
10 del self._content
11
12 #设置队列的大小
13 def setSize(self,size):
14 if size < self._current:
15 #如果缩小队列,应删除后面的元素
16 for i in range(size,self._current)[::-1]:
17 del self._content[i]
18 self._current = size
19 self._size = size
20
21 #入队
22 def put(self,v):
23 if self._current < self._size:
24 self._content.append(v)
25 self._current = self._current + 1
26 else:
27 print(‘The queue is full‘)
28
29 #出队
30 def get(self):
31 if self._content:
32 self._current = self._current - 1
33 return self._content.pop(0)
34 else:
35 print(‘The queue is empty‘)
36
37 def show(self):
38 if self._content:
39 print(self.content)
40 else:
41 print(‘The queue is empty‘)
42
43 #把队列置空
44 def empty(self):
45 self._content = []
46 self._current = 0
47
48 #判断队列是否为空
49 def isEmpty(self):
50 if not self._content:
51 return True
52 else:
53 return False
54
55
56 #判断队列是否满了
57 def isFull(self):
58 if self._current == self._size:
59 return True
60 else:
61 return False
62
63 if __name__ == ‘__main__‘:
64 print(‘Please use me as a module.‘)
1 #导入包含自定义队列类的模块
2 >>>from myQueue import myQueue
3
4 #创建自定义队列对象
5 >>> q = myQueue()
6
7 #获取队列元素
8 >>> q.get()
9 The queue is empty
10
11 #在队列尾部插入元素
12 >>> q.put(5)
13 >>> q.put(7)
14
15 #判读队列是否已满
16 >>> q.isFull()
17 False
18 >>> q.put(‘a‘)
19 >>> q.put(3)
20 >>> q.show()
21 [5, 7, ‘a‘, 3]
22 >>>
23 >>> q.setSize(3)
24
25 #查看队列中的所有元素
26 >>> q.show()
27 [5, 7, ‘a‘]
28 >>>
29 >>> q.put(10)
30 The queue is full
31 >>>
32
33 #修改队列的大小
34 >>> q.setSize(5)
35 >>> q.put(10)
36 >>> q.show()
37 [5, 7, ‘a‘, 10]
38 >>>
拓展知识:Python 标准库queue 提供了LILO队列类Queue、LIFO队列类LifoQueue、优先级队列类PriorityQueue,标准库 collections 提供了双端队列。例如:
>>> #LILO队列
>>> from queue import Queue
>>>
>>> #创建队列对象
>>> q = Queue()
>>> q.put(0)
>>> q.put(1)
>>> q.put(2)
>>>
>>> #查看队列中的所有元素
>>> print(q.queue)
deque([0, 1, 2])
>>>
>>> #返回并删除队列头部元素
>>> q.get()
0
>>> q.get()
1
>>> q.queue
deque([2])
>>>
1 >>> #LIFO队列
2 >>> from queue import LifoQueue
3 >>>
4 >>> #创建LIFO队列对象
5 >>> q = LifoQueue()
6 >>>
7 >>> #在队列尾部插入元素
8 >>> q.put(1)
9 >>> q.put(2)
10 >>> q.put(3)
11 >>>
12 >>> #查看队列中的所有元素
13 >>> print(q.queue)
14 [1, 2, 3]
15 >>>
16 >>> #返回并删除队列尾部元素
17 >>> q.get()
18 3
19 >>> q.get()
20 2
21 >>>
22 >>> q.queue
23 [1]
24 >>>
1 >>>
2 >>> #优先级队列
3 >>> from queue import PriorityQueue
4 >>>
5 >>> #创建优先级队列对象
6 >>> q = PriorityQueue()
7 >>>
8 >>> #插入元素
9 >>> q.put(3)
10 >>> q.put(8)
11 >>> q.put(100)
12 >>>
13 >>> #查看优先级队列中的所有元素
14 >>> q.queue
15 [3, 8, 100]
16 >>>
17 >>> #再插入元素,自动调整优先级队列
18 >>> q.put(1)
19 >>> q.put(2)
20 >>> q.queue
21 [1, 2, 100, 8, 3]
22 >>>
23 >>> #返回并删除优先级最低的元素
24 >>> q.get()
25 1
26 >>> q.get()
27 2
28 >>> q.get()
29 3
30 >>> q.get()
31 8
32 >>> q.get()
33 100
34 >>> q.get()
1 >>>
2 >>> #导入双端队列
3 >>> from collections import deque
4 >>>
5 >>> #创建双端队列实例
6 >>> q = deque([‘Eric‘,‘John‘,‘Smith‘])
7 >>> q
8 deque([‘Eric‘, ‘John‘, ‘Smith‘])
9 >>>
10 >>> #在右侧插入新元素
11 >>> q.append(‘Tom‘)
12 >>> q
13 deque([‘Eric‘, ‘John‘, ‘Smith‘, ‘Tom‘])
14 >>>
15 >>> #在左侧插入新元素
16 >>> q.appendleft(‘Terry‘)
17 >>> q
18 deque([‘Terry‘, ‘Eric‘, ‘John‘, ‘Smith‘, ‘Tom‘])
19 >>>
20 >>> #返回并删除队列最右端元素
21 >>> q.pop()
22 ‘Tom‘
23 >>>
24 >>> q
25 deque([‘Terry‘, ‘Eric‘, ‘John‘, ‘Smith‘])
26 >>>
27 >>> #返回并删除队列最左端元素
28 >>> q.popleft()
29 ‘Terry‘
30 >>>
31 >>> q
32 deque([‘Eric‘, ‘John‘, ‘Smith‘])
33 >>>