理论部分
- 用数组实现一个顺序队列。
- 用数组实现一个循环队列。
- 用链表实现一个链式队列。
队列: 是一种先进先出(FIFO)的线性表,它只允许在表的一端插入元素,而在表的另一端删除元素。在队列中,允许插入元素的一端称为队尾(Rear),允许删除元素的一端称为对头(Front)。
顺序队列: 队列的顺序存储结构是指利用一组地址连续的存储单元存放队列的元素。
循环队列: 将顺序队列假想成一个环状结构,称之为循环队列。
链队列: 用链表表示的队列简称为链队列。
练习部分
- 模拟银行服务完成程序代码。
目前,在以银行营业大厅为代表的窗口行业中大量使用排队(叫号)系统,该系统完全模拟了人群排队全过程,通过取票进队、排队等待、叫号服务等功能,代替了人们站队的辛苦。
排队叫号软件的具体操作流程为:
顾客取服务序号
当顾客抵达服务大厅时,前往放置在入口处旁的取号机,并按一下其上的相应服务按钮,取号机会自动打印出一张服务单。单上显示服务号及该服务号前面正在等待服务的人数。
服务员工呼叫顾客
服务员工只需按一下其柜台上呼叫器的相应按钮,则顾客的服务号就会按顺序的显示在显示屏上,并发出“叮咚”和相关语音信息,提示顾客前往该窗口办事。当一位顾客办事完毕后,柜台服务员工只需按呼叫器相应键,即可自动呼叫下一位顾客。
编写程序模拟上面的工作过程,主要要求如下:
程序运行后,当看到“请点击触摸屏获取号码:”的提示时,只要按回车键,即可显示“您的号码是:XXX,您前面有YYY位”的提示,其中XXX是所获得的服务号码,YYY是在XXX之前来到的正在等待服务的人数。
用多线程技术模拟服务窗口(可模拟多个),具有服务员呼叫顾客的行为,假设每个顾客服务的时间是10000ms,时间到后,显示“请XXX号到ZZZ号窗口!”的提示。其中ZZZ是即将为客户服务的窗口号。
import time
import threading
# 实现栈这个类
class Queue:
def __init__(self):
self.items = []
def isEmpty(self):
return self.items == []
def enqueue(self, item):
self.items.insert(0,item)
def dequeue(self):
if self.items != []:
return self.items.pop()
else:
return False
def size(self):
return len(self.items)
def top(self):
if self.items != []:
return self.items[len(self.items)-1]
else:
return False
# 实现银行柜台叫号功能
class Counter(threading.Thread):
def __init__(self):
threading.Thread.__init__(self)
self.waitQueue = Queue() # 初始化等待的队伍
self.lock = threading.Lock()
def callIng(self):
while True:
# 柜台一直叫号,要一直循环
time.sleep(10)
if not self.waitQueue.isEmpty():
self.lock.acquire()
print("请{}号客户,到{}号窗口办理业务".format(self.waitQueue.top(), threading.current_thread().name))
self.waitQueue.dequeue()
self.lock.release()
class bankSystem:
def __init__(self):
self.serviceQueue = Queue()
self.nowNum = 0
# self.windows = k # 银行柜台数目
self.maxSize = 100
def getNumber(self):
if self.nowNum < self.maxSize:
self.nowNum += 1
return self.nowNum
else:
print("现在业务繁忙,请稍后再来")
if __name__ == "__main__":
bank_sys = bankSystem()
windowcount = 3
serviceWindow = [None] * windowcount
threadList = [None] * windowcount
for i in range(windowcount):
serviceWindow[i] = Counter()
serviceWindow[i].waitQueue = bank_sys.serviceQueue
threadList[i] = threading.Thread(name=(i + 1), target=serviceWindow[i].callIng, args=())
threadList[i].start()
# threadList[i].join()
while True:
input("请点击触摸屏获取号码:")
callNumber = bank_sys.getNumber()
if bank_sys.serviceQueue != None:
print("当前您的的号码为{},您前面还有{}个人".format(str(callNumber), str(bank_sys.serviceQueue.size())))
bank_sys.serviceQueue.enqueue(bank_sys.nowNum)
else:
print('您的号码是:{},您前面有 0 位'.format(callNumber))