Простое моделирование очереди

Я пытаюсь смоделировать очередь с ограниченным буфером, в которой ни один пакет не отбрасывается, но находится в ожидании. Потерпите меня, так как я всего лишь студент с базовыми навыками кодирования.

Пакет поступает экспоненциально распределенным, и каждый из них содержит средний размер пакета 1250 байт. Мне удалось заставить код работать для прибытия пакета + время обработки, но я не мог заставить пакет «отправиться», а также имитировать очередь (пока что это с неограниченным буфером). Есть ли что-нибудь, что я мог бы сделать для имитации отправления пакета и лимит очереди?

код:

import random
import simpy

RANDOM_SEED = 42
NEW_CUSTOMERS = 100  # Total number of customers
INTERVAL_CUSTOMERS = 1  # Generate new customers roughly every x seconds
SIZE = 1250

def source(env, number, interval, port):
    """Source generates packet randomly"""
    for i in range(number):
        size =  int(random.expovariate(0.0008))
        packet = Packet(env, '%d' % i, size, port, time_in_port=1)
        env.process(packet)
        t = random.expovariate(1 / interval)
        yield env.timeout(t)

def Packet(env, id, size, port, time_in_port):
    arrive = env.now
    yield Queue.buffer.put(size)
    print('packet%s %s arriving at %lf' % (id, size, arrive))

    with port.request() as req:
        yield req

        tip = random.expovariate(1/time_in_port)
        yield env.timeout(tip)
        amount = size
        yield Queue.buffer.get(amount)
        print('packet%s %s finished processing at %lf' % (id, size, env.now))

class queue:     #THIS PART WON'T WORK
    def __init__(self, env):
        self.port = simpy.Resource(env, capacity=1)
        self.buffer = simpy.Container(env, init = 0, capacity=12500)
        self.mon_proc = env.process(self.monitor_tank(env))

    def monitor_tank(self, env):
        while True:
           if self.buffer.level > 12500:
             print('Full at %d' % env.now)


random.seed(RANDOM_SEED)
env = simpy.Environment()
Queue = queue(env)

port = simpy.Resource(env, capacity=1)
env.process(source(env, NEW_CUSTOMERS, INTERVAL_CUSTOMERS, port))
env.run()

Класс очереди не работал (программа вообще не запускается). Он будет работать, если только я удалю класс очереди и смоделирую время прибытия и обработки пакетов. Буду признателен за любую помощь, чтобы заставить меня имитировать отправку пакета (используя приемник) и ограничение очереди. Спасибо.


person fieq.fikri    schedule 09.04.2018    source источник


Ответы (3)


Не знаком с деталями, но ваш вызов self.monitor_tank(env) в конструкторе queue войдет в жесткий бесконечный цикл - это не генератор, просто бесконечный цикл, поэтому python застрянет в этой точке выполнения. .

person sfjac    schedule 10.04.2018

Я думаю, что этот код из вашего кода представляет собой бесконечный цикл и блокирует запуск вашего кода.

def monitor_tank(self, env):
        while True:
           if self.buffer.level > 12500:
             print('Full at %d' % env.now)

Попробуйте прокомментировать этот кусок или добавить env.timeout, чтобы он немного спал при каждом проходе цикла.

person Michael    schedule 19.05.2021

Здравствуйте, я думаю, что код решит вашу проблему или, по крайней мере, даст вам направление. Поскольку в вашем исходном коде все пакеты имеют одинаковый размер, я смоделировал эти пакеты, но перейти на байты просто.

Я использовал буфер (контейнер) и сервер (ресурс).

;)

import simpy
import random     

def arrival(env, buffer):
  #Arrival of the Package

  while True:
    print('Package ARRIVED at %.1f \n\t Buffer: %i' 
                      % (env.now, buffer.level))
    yield buffer.put(1) # Put the package in the buffer
    yield env.timeout(random.expovariate(1.0)) # time between arrivals
    env.process(processDeparture(env, buffer, server)) 

def processDeparture(env, buffer, server):
  #Processing and Departure of the Package

  while True:
    
    # request a Server to process thge package
    request = server.request()
    yield request

    yield buffer.get(1) # GET a package from the buffer

    # Processing time of the package
    processingTime = 2
    print('Package begin processing at %.1f'
                      % (env.now))
    yield env.timeout(processingTime)
    print('Package end processing at %.1f'
                      % (env.now))
    # release the server
    yield server.release(request)


random.seed(150)            
env = simpy.Environment()
buffer = simpy.Container(env, capacity=3, init=0)  # Create the Buffer 
server = simpy.Resource(env, capacity=1)           # Create the servers (resources)

env.process(arrival(env, buffer))         

env.run(until=30)                                # Execute the Model
person Eduardo Pécora    schedule 19.05.2021