如何关联Simpy中Environment.any_of返回字典的对应Store或进程
解决Simpy中
any_of结果关联对应Store/进程的问题 我完全懂你的困扰——Environment.any_of()返回的字典里,键是StoreGet对象,但默认情况下这些对象没法直接告诉你它们属于哪个Store或者对应的worker进程。不过我们可以通过自定义带标识的事件来解决这个问题,下面是具体的实现思路和代码:
核心思路:给StoreGet事件绑定标识
Simpy的事件类支持继承扩展,我们可以创建一个IdentifiedStoreGet子类,把Store的引用或者worker的ID直接绑定到事件上,这样后续从事件对象里就能直接拿到关联信息了。
完整代码示例
import simpy import random # 自定义带标识的StoreGet事件,继承自原生StoreGet class IdentifiedStoreGet(simpy.events.StoreGet): def __init__(self, store, worker_id=None): super().__init__(store) self.worker_id = worker_id # 绑定对应的worker进程ID self.store = store # 直接绑定所属的Store对象 def worker(ident, env, sstore): while True: # 随机等待模拟业务耗时 yield env.timeout(random.randint(1, 5)) # 用自定义事件替代原生store.get(),传入当前worker的ID get_event = IdentifiedStoreGet(sstore, ident) yield get_event print(f"Worker {ident} 拿到数据: {get_event.value} | 当前时间: {env.now}") def monitor(env, store_list): while True: # 为每个Store创建带标识的get事件 get_events = [IdentifiedStoreGet(store, idx) for idx, store in enumerate(store_list)] # 等待任意一个get事件完成 done_events, pending_events = yield env.any_of(get_events) # 遍历完成的事件,直接获取关联的worker/Store信息 for event in done_events: print(f"监控器发现: Worker {event.worker_id} (对应Store: {event.store}) 在时间 {env.now} 取出了数据 {event.value}") # 取消未完成的事件,避免内存泄漏 for event in pending_events: event.cancel() # 初始化模拟环境 env = simpy.Environment() # 创建3个专属Store,对应3个worker进程 worker_stores = [simpy.Store(env) for _ in range(3)] # 启动worker并给每个Store初始化数据 for i in range(3): env.process(worker(i, env, worker_stores[i])) worker_stores[i].put(f"Worker{i}_数据1") worker_stores[i].put(f"Worker{i}_数据2") # 启动监控进程 env.process(monitor(env, worker_stores)) # 运行模拟20个时间单位 env.run(until=20)
关键细节解释
- 自定义事件类:
IdentifiedStoreGet继承自原生StoreGet,额外添加了worker_id(进程ID)和store(Store对象)两个属性,让事件本身携带关联信息。 - Worker进程的事件创建:不再直接调用
store.get(),而是实例化自定义事件并传入当前worker的ID,确保事件和进程绑定。 - 监控逻辑的处理:在
any_of返回的done_events中,每个事件对象都带有我们预先绑定的标识,直接通过event.worker_id或event.store就能精准对应到所属的进程或Store。
这样你就能轻松把any_of的返回结果和对应的Store/进程关联起来了。
内容的提问来源于stack exchange,提问作者Selma Re
相关产品推荐
相关产品推荐

