一步一步学python之(26)队列-PriorityQueue优先级队列

1. 简介

优先队列是一种特殊的队列,队列中的元素按照其优先级进行排序。优先级可以由元素自身的值决定,也可以由自定义的比较规则决定。在 Python 中,可以通过 queue 模块中的 PriorityQueue 类来实现优先队列。PriorityQueue 类内部使用堆结构来实现,保证每次出队操作都能获取到优先级最高的元素。
优先队列在许多场景中都非常有用,例如任务调度(高优先级任务先执行)、消息队列(重要消息先处理)、Dijkstra 算法(最短路径优先)等。

2. PriorityQueue 类的基本操作

队列的操作其实很多都是相同或相似的,比如入队,出队等操作。只是每个特定操作可能有一些不同。

(1)创建队列

使用 queue.PriorityQueue() 可以创建一个优先队列。可以通过设置 maxsize 参数来指定队列的最大容量。如果 maxsize 小于或等于 0,则队列大小无限。
样例:

import queue

# 创建一个空的优先队列,最大容量为 3
priority_queue = queue.PriorityQueue(maxsize=3)
print("创建的优先队列:", priority_queue)

程序运行结果:
在这里插入图片描述

(2)入队(向队列中添加元素)

put(item, block=True, timeout=None)
将元素 item 放入队列中。如果队列已满,且 block 参数为 True,则线程会阻塞,直到队列有空间。如果 block 为 False,则会抛出 queue.Full 异常。timeout 参数指定线程阻塞等待的时间,单位为秒。
在优先队列中,元素通常是元组形式,例如 (优先级, 数据),队列会根据元组的第一个元素(优先级)进行排序。优先级数字越小的元素优先级越高,会先出队。优先级数字越小优先级就越高!!!

import queue

priority_queue = queue.PriorityQueue(maxsize=3)

# 向队列中添加元素(元组形式,第一个元素为优先级)
print("初始队列是否为空:", priority_queue.empty())

priority_queue.put((1, "陪赔家人"))
priority_queue.put((2, "挣money"))
priority_queue.put((3, "吃喝玩乐"))

# 尝试继续添加元素(阻塞,此处会等待直到有空间)
# priority_queue.put((4, "睡觉"), block=True, timeout=5)

print("队列元素(按优先级排序):")
for _ in range(priority_queue.qsize()):
    print(priority_queue.queue[_])

程序运行结果:

在这里插入图片描述
可以看出先输出的是1,陪陪家人,其次是2 挣money,最后是吃喝玩乐。题外话(1我相信应该是最重要的,但是现实中往往大多数人看中的是2。)

(3)出队

get(block=True, timeout=None)
从队列中移除并返回优先级最高的元素。如果队列为空,且 block 参数为 True,则线程会阻塞,直到队列有元素。如果 block 为 False,则会抛出 queue.Empty 异常。timeout 参数指定线程阻塞等待的时间,单位为秒。
样例:

import queue

priority_queue = queue.PriorityQueue(maxsize=3)
priority_queue.put((1, "陪赔家人"))
priority_queue.put((2, "挣money"))
priority_queue.put((3, "吃喝玩乐"))

# 从队列中移除元素(按优先级顺序)
print("出队的元素:")
while not priority_queue.empty():
    item = priority_queue.get()
    print(item)

程序运行结果:

在这里插入图片描述

(4)队列状态

  • empty()

如果队列为空,返回 True;否则返回 False。

  • full()

如果队列已满,返回 True;否则返回 False。

样例:

import queue

priority_queue = queue.PriorityQueue(maxsize=3)

# 判断队列是否为空
print("队列是否为空:", priority_queue.empty())

# 向队列中添加元素
priority_queue.put((1, "陪赔家人"))
priority_queue.put((2, "挣money"))
priority_queue.put((3, "吃喝玩乐"))

# 判断队列是否已满
print("队列是否已满:", priority_queue.full())

# 移除一个元素后,判断队列状态
priority_queue.get()
print("移除一个元素后,队列是否为空:", priority_queue.empty())
print("移除一个元素后,队列是否已满:", priority_queue.full())

程序运行结果:
在这里插入图片描述

(5)队列大小

  • qsize()

返回队列中元素的大致数量。
样例:

import queue

priority_queue = queue.PriorityQueue(maxsize=3)

# 获取队列初始大小
print("队列初始大小:", priority_queue.qsize())

# 向队列中添加元素并获取队列大小
priority_queue.put((1, "陪陪家人"))
print("添加一个元素后队列大小:", priority_queue.qsize())

priority_queue.put((2, "挣money"))
priority_queue.put((3, "吃喝玩乐"))
print("添加三个元素后队列大小:", priority_queue.qsize())

程序运行结果:

在这里插入图片描述

3. 总结

优先队列是一种重要的数据结构,可以通过 queue 模块中的 PriorityQueue 类来实现。它的主要特点是元素按照优先级进行排序,每次出队操作都能获取到优先级最高的元素,优先级数字越小代表优先级越高。优先队列适用于任务调度、Dijkstra 算法、事件驱动模拟等多种场景。
PriorityQueue 类的常用方法包括 put()(入队)、get()(出队)、empty()(判断队列是否为空)、full()(判断队列是否已满)和 qsize()(获取队列大小)。通过这些方法,可以在多线程环境下安全地操作优先队列。

Logo

腾讯云面向开发者汇聚海量精品云计算使用和开发经验,营造开放的云计算技术生态圈。

更多推荐