You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Python线程实现无性别卫生间:性别隔离规则失效问题排查

搞定无性别卫生间的性别隔离:LightSwitch模式的正确打开方式

嘿,我完全懂这种面试卡壳的挫败感——LightSwitch模式乍一看好像适配这个场景,但实际用起来就会发现性别隔离的漏洞,咱们一步步拆解问题,把它捋明白!

先搞懂:为什么你用的LightSwitch会失效?

LightSwitch模式的核心是管理同类型进程的批量进入/退出(比如多读者共享临界区),但它本身不处理不同类型进程之间的互斥。如果只是给男性、女性各套一个独立的LightSwitch,相当于两个群体各玩各的——男性的LightSwitch允许N个男性进,女性的允许N个女性进,但两者之间没有任何互斥机制,自然会出现异性同时在卫生间的情况。

举个错误实现的例子(大概率是你面试时踩的坑):

import threading

# 标准LightSwitch实现,但用错了地方
class LightSwitch:
    def __init__(self):
        self.count = 0
        self.mutex = threading.Lock()

    def lock(self, semaphore):
        with self.mutex:
            self.count += 1
            if self.count == 1:
                semaphore.acquire()

    def unlock(self, semaphore):
        with self.mutex:
            self.count -= 1
            if self.count == 0:
                semaphore.release()

# 错误的卫生间实现:两个性别各用独立信号量,无全局互斥
class Bathroom:
    def __init__(self):
        self.male_sem = threading.Semaphore(1)
        self.female_sem = threading.Semaphore(1)
        self.male_switch = LightSwitch()
        self.female_switch = LightSwitch()

    def male_enter(self):
        self.male_switch.lock(self.male_sem)
        print("男性进入卫生间")

    def male_leave(self):
        print("男性离开卫生间")
        self.male_switch.unlock(self.male_sem)

    def female_enter(self):
        self.female_switch.lock(self.female_sem)
        print("女性进入卫生间")

    def female_leave(self):
        print("女性离开卫生间")
        self.female_switch.unlock(self.female_sem)

这里的问题很明显:male_sem和female_sem是完全独立的,男性群体和女性群体的进入操作互不干扰,根本达不到性别隔离的目的。

修正方案:LightSwitch + 全局性别互斥锁

正确的思路是:用LightSwitch管理同性别群体的批量进出,再用一个全局互斥锁保证不同性别群体之间的排他性。具体实现如下:

import threading

class LightSwitch:
    def __init__(self):
        self.count = 0
        self.mutex = threading.Lock()

    def lock(self, global_mutex):
        with self.mutex:
            self.count += 1
            # 第一个进入的同性别用户,抢占全局性别互斥锁
            if self.count == 1:
                global_mutex.acquire()

    def unlock(self, global_mutex):
        with self.mutex:
            self.count -= 1
            # 最后一个离开的同性别用户,释放全局性别互斥锁
            if self.count == 0:
                global_mutex.release()

class Bathroom:
    def __init__(self):
        # 全局互斥锁:同一时间只能有一个性别的群体进入
        self.gender_mutex = threading.Lock()
        self.male_switch = LightSwitch()
        self.female_switch = LightSwitch()

    def male_enter(self):
        # 男性群体通过LightSwitch统一抢占全局锁
        self.male_switch.lock(self.gender_mutex)
        print("男性进入卫生间")

    def male_leave(self):
        print("男性离开卫生间")
        self.male_switch.unlock(self.gender_mutex)

    def female_enter(self):
        # 女性群体同理,若全局锁被男性占用则阻塞
        self.female_switch.lock(self.gender_mutex)
        print("女性进入卫生间")

    def female_leave(self):
        print("女性离开卫生间")
        self.female_switch.unlock(self.gender_mutex)

关键修正点解析:

  1. 全局性别互斥锁:gender_mutex是整个卫生间的“准入令牌”,同一时间只有一个性别群体能持有它。
  2. LightSwitch的作用:它负责统计同性别进入的人数,只有第一个人需要去抢占全局锁,最后一个人需要释放全局锁——这样既保证了同性别可以无限进入(符合容量无限的要求),又保证了异性无法同时进入。

总结一下核心逻辑

  • 同性别群体:通过LightSwitch实现“批量进入/退出”,避免每个用户都去抢锁,提升效率。
  • 不同性别群体:通过全局互斥锁实现严格排他,保证同一时间只有单一性别人群使用卫生间。

下次面试遇到类似问题,记住这个组合拳就行啦!

内容的提问来源于stack exchange,提问作者Wrddot

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.05.21 06:59:34