【问题标题】:simpy 2.2 examples in 3.0simpy 3.0 中的 2.2 示例
【发布时间】:2016-05-24 00:14:38
【问题描述】:

我正在尝试研究 simpy 2.2 的一些示例(请参阅:https://pythonhosted.org/SimPy/Tutorials/TheBank2OO.html)并使用 simpy 3.0 词典重写它们(请参阅:http://simpy.readthedocs.io/en/latest/about/history.html)。有没有人遇到过为 3.0 重写的以下示例(银行门打开)?我不完全确定如何使用 simpy 3.0 将“customer”类中的“self.sim.door_open”编写为事件。

from SimPy.Simulation import     Simulation,Process,Resource,hold,waituntil,request,release
from random import expovariate,seed

##Model components ------------------------

class Doorman(Process):                                       
    """ Doorman opens the door"""
    def openthedoor(self):
        """ He will open the door when he arrives"""
        yield hold,self,expovariate(1.0/10.0)                 
        self.sim.door = 'Open'                                           
        print "%7.4f Doorman: Ladies and "\
              "Gentlemen! You may all enter."%(self.sim.now(),)

class Source(Process):                                        
    """ Source generates customers randomly"""
    def generate(self,number,rate):       
        for i in range(number):
            c = Customer(name = "Customer%02d"%(i,),sim=self.sim)
            self.sim.activate(c,c.visit(timeInBank=12.0))
            yield hold,self,expovariate(rate)

class Customer(Process):                                      
    """ Customer arrives, is served and leaves """
    def visit(self,timeInBank=10):       
        arrive = self.sim.now()

        if self.sim.dooropen():
            msg = ' and the door is open.'         
        else:
            msg = ' but the door is shut.'
        print "%7.4f %s: Here I am%s"%(self.sim.now(),self.name,msg)

        yield waituntil,self,self.sim.dooropen                         

        print "%7.4f %s: I can  go in!"%(self.sim.now(),self.name)     
        wait = self.sim.now()-arrive
        print "%7.4f %s: Waited %6.3f"%(self.sim.now(),self.name,wait)

        yield request,self,self.sim.counter
        tib = expovariate(1.0/timeInBank)
        yield hold,self,tib
        yield release,self,self.sim.counter

        print "%7.4f %s: Finished    "%(self.sim.now(),self.name)                                 

## Model  ----------------------------------

class BankModel(Simulation):
    def dooropen(self):                                               
        return self.door=='Open'

    def run(self,aseed):
        self.initialize()
        seed(aseed)
        self.counter = Resource(capacity=1,name="Clerk",sim=self)
        self.door = 'Shut'
        doorman=Doorman(sim=self)                                          
        self.activate(doorman,doorman.openthedoor())                    
        source = Source(sim=self)                                                         
        self.activate(source,
             source.generate(number=5,rate=0.1),at=0.0)    
        self.simulate(until=400.0)

## Experiment data -------------------------

maxTime = 2000.0   # minutes    
seedVal = 393939

## Experiment  ----------------------------------

BankModel().run(aseed=seedVal)

到目前为止,我得到了错误“环境对象没有属性'door_open'”

import simpy
import random

忍者编辑:我设法让模拟运行,但是我无法让门初始化为“关闭”然后在某个时候打开。

def openthedoor(self):
    yield self.timeout(random.expovariate(1.0 /10.0))
    print('%7.4f Doorman: ladies and gentleman you may enter' %(self.now))



def source(env, name, counter):

     for i in range(500):
        env.process(customer(env, 'Customer%02d' % i, counter,      time_in_queue=30.0))
        t = random.expovariate(1.0 / 20.0)
        yield env.timeout(t)

def customer(env, name, counter, time_in_queue):
    arrive = env.now

    if env.process.openthedoor(env):
        msg = 'and the door is open'
    else:
        msg = 'but the door is sht'
        print('%7.4f %s: Customer has entered queue and' % (arrive, name, msg))

    yield env.process(openthedoor(env))
    print('%7.4f %s: I can go in' % (env.now, name))
    wait = env.now - arrive
    print('%7.4f %s: Waited %6.3f' % (env.now, name, wait))

    with counter.request() as req:
        # Wait for the counter or abort at the end of our tether
        yield req 
        waited = env.now - arrive
        tib = random.expovariate(1.0 / 20.0)
        yield env.timeout(tib)
        print('%7.4f %s: Waited %6.3f' % (env.now, name, waited))
        print('%7.4f %s: Finished' % (env.now, name))

print('Batch Record Review Simulation')
random.seed(RANDOM_SEED)
env = simpy.Environment()
data = []
counter = simpy.Resource(env, capacity=1)
env.process(source(env, CUSTOMERS, counter))
# Start processes and run


env.run(until=SIM_TIME)

【问题讨论】:

    标签: python simulation simpy


    【解决方案1】:

    在 SimPy 2 中,waituntil 使用“忙等待”,这意味着它会在每一步检查条件评估为 True。这不是很好的做法,可能会消耗大量 CPU 时间。这就是 SimPy 3 中不再有此功能的原因。

    在 SimPy 3 中,您将使用普通的 Event(由 Environment.event() 创建)。例如,您可以创建一个Door 类并将门实例的引用传递给开门器和客户。客户每次想要开门时都可以发送door.open = env.event()。然后开门器将触发该事件。

    另一种解决方案可能是使用PriorityResource(或者可能是`PreemptiveResource)作为门。开门器使用比客户更高的优先级,因此能够“阻止”门(== 门关闭)。一旦开门器释放资源,下一个客户就可以“打开”门。

    【讨论】:

    • 感谢您的回复!顺便说一句,您认为有可能以这样一种方式使用优先资源来周期性地(在定期的、非随机的时间间隔内)打开和关闭门吗?也许使用单独的线程来更改相对于系统时钟(每分钟)的资源优先级并设置为模拟以实时运行?根据我的阅读,随着时间的推移改变资源容量并非易事。也许我误解了线程是如何工作的?无论如何,再次感谢。
    • 您无法更改内置资源的容量。你必须编写自己的类型来实现这一点。
    猜你喜欢
    • 1970-01-01
    • 2016-12-06
    • 1970-01-01
    • 1970-01-01
    • 2011-04-26
    • 1970-01-01
    • 2012-07-24
    • 1970-01-01
    • 2014-05-23
    相关资源
    最近更新 更多