首页
学习
活动
专区
圈层
工具
发布
首页
学习
活动
专区
圈层
工具
MCP广场
社区首页 >问答首页 >对Hilzer理发店问题解的理解

对Hilzer理发店问题解的理解
EN

Stack Overflow用户
提问于 2020-01-11 21:56:56
回答 1查看 1.3K关注 0票数 0

问题

这是“信号量小书”中的一个问题。

我们的理发店有三把椅子,三位理发师,以及一个可以在沙发上容纳四位顾客的等候区,可以容纳更多的顾客。消防守则限制商店内的顾客总数为20人。

顾客如与其他顾客合二为一,将不会进入本店。一旦进入,顾客就会在沙发上坐下,或者如果沙发满了,就站在那里。当理发师有空的时候,在沙发上呆得时间最长的顾客就会得到服务,如果有任何顾客站在沙发上,那么在店里呆得时间最长的顾客就会坐在沙发上。当顾客理发完毕后,任何理发师都可以接受付款,但由于只有一个收银机,所以每次只接受一个顾客付款。酒吧老板们把时间分配在剪头发、接受报酬和睡在椅子上等着顾客上。

书本解决方案

以下是本书的解决方案:

共享变量

代码语言:javascript
运行
复制
customers = 0
mutex = Semaphore(1)
mutex2 = Semaphore(1)
sofa = Semaphore(4)
customer1 = Semaphore(0)
customer2 = Semaphore(0)
payment = Semaphore(0)
receipt = Semaphore(0)
queue1 = []
queue2 = []

客户线程

代码语言:javascript
运行
复制
self.sem1 = Semaphore(0)
self.sem2 = Semaphore(0)

mutex.wait()
    if customers == 20:
        mutex.signal()
        balk()
    customers += 1
    queue1.append(self.sem1)
mutex.signal()

# enterShop()
customer1.signal()
self.sem1.wait()

sofa.wait()
    # sitOnSofa()
    self.sem1.signal()
    mutex2.wait()
        queue2.append(self.sem2)
    mutex2.signal()
    customer2.signal()
    self.sem2.wait()
sofa.signal()

# getHairCut()

mutex.wait()
    # pay()
    payment.signal()
    receipt.wait()
    customers -= 1
mutex.signal()

理发螺纹

代码语言:javascript
运行
复制
customer1.wait()
mutex.wait()
    sem = queue1.pop(0)
    sem.signal()
    sem.wait()
mutex.signal()

customer2.wait()
mutex2.wait()
    sem2 = queue2.pop(0)
    sem2.signal()
mutex2.signal()

# cutHair()
payment.wait()
# acceptPayment()
receipt.signal()

问题

据我所知,当第一个顾客(客户1)进来,理发师(理发师1)睡在customer1上时,可以执行以下步骤

  1. Customer 1向queue1添加自己的信号量,向queue1发送信号,并等待自己的queue11唤醒,从customer1队列中弹出客户1的信号量,向它发出信号(唤醒客户1),并等待它。此时,理发师1持有mutex.
  2. Customer 1,所以在理发师1醒来并释放mutex.

1之前,没有任何其他免费理发师可以让顾客进入理发店,通过sofa (减去它并使它成为3),并发出自己的信号量(醒来理发师1)。

  • 理发师1醒来并向mutex.

发出信号。

在这一点上,没有什么能阻止另一个客户经历相同的过程,并最终在客户1之前到达queue2

因此,我很难理解这本书的解决方案是如何执行这样的约束:“如果有任何站立的顾客,在商店里最长的人就坐在沙发上”。

为了执行这个命令,客户线程似乎应该只在它将自己添加到queue2之后才向self.sem1发出信号,而不是之前。

有人能帮我理解这个解决方案吗?

EN

回答 1

Stack Overflow用户

发布于 2020-01-12 17:29:01

首先,请注意,理发线从代表沙发的queue2头上提取客户,因此,一旦理发师拉起客户,该客户就是在沙发上等待时间最长的客户。

其次,请注意,一旦客户被从queue2中拉出来,理发本身就不需要任何时间,客户就会转移到付款。因此,它的写作方式,客户被拉出队列,并立即移动付款。理发是瞬间的。

因此,如果另一位顾客来了并穿过队列,那么唯一可以选择的方法是,如果有另一位理发师,而第二位顾客在排队的最前面。但是,如果第二个顾客排在第一位,那就意味着另一个理发师已经选择了第一个顾客。所以,这真的不可能发生。

关于self.sem1的问题:它的目的是在客户从队列中被选中后唤醒客户。sem1对应于顾客站立的队列,sem2对应于沙发。客户将信号量添加到队列中,并等待它,因此当理发师线程捡起它时,它可以唤醒客户。因此,它不能真正强制订货,它是在那里唤醒客户时,他/她改变位置。排序由队列强制执行。

票数 0
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/59698987

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档