import agentpy as ap import numpy as np import pandas as pd from collections import deque class InventorySystem(ap.Agent): xv_ary_initial_material_num: np.ndarray # 初始原材料库存 xv_ary_initial_product_num: np.ndarray # 初始产成品库存 ev_ary_current_material: np.ndarray # 当期原材料库存 ev_ary_current_product: np.ndarray # 当期产成品库存 ev_ary_material_state_to_use: np.ndarray # 当期预期使用的原材料 ev_ary_material_to_use: np.ndarray # 当期实际消耗的原材料 ev_ary_is_order_material: np.ndarray # 是否订购产品 ev_ary_num_material_to_order: np.ndarray # 订购数量 ev_ary_num_material_order_done: np.ndarray # 当期送到的数量 # set the lead time of material replenishment xv_ary_lead_time: np.ndarray # 原材料订货的等待时间 # the list of materials in transit ev_lst_trans_quan_material: list # Iss传递给Pss的原材料数量 ev_lst_backtrans_quan_material: list # Pss退回的原材料数量 # Material list xv_ary_material: np.ndarray xv_ary_bom: np.ndarray # 原材料订购的开始时间和到达时间 ev_ary_order_time: np.ndarray ev_ary_arrive_time: np.ndarray xv_product_num: int xv_material_num: int xv_ary_plan: np.ndarray def setup(self, xv_ary_initial_material_num, xv_ary_initial_product_num, xv_product_num, xv_material_num, xv_ary_bom, xv_ary_plan, xv_ary_material_id): # Set up the initial inventory quantity self.xv_ary_initial_material_num = xv_ary_initial_material_num self.xv_ary_initial_product_num = xv_ary_initial_product_num self.ev_ary_current_material = xv_ary_initial_material_num # 115*2 self.ev_ary_current_product = xv_ary_initial_product_num # 23*2 self.xv_product_num = xv_product_num # 产成品个数 self.xv_material_num = xv_material_num # 原材料个数 self.ev_ary_num_material_order_done = np.zeros((xv_material_num,)) # 当期原材料送到的数量 115x1 # set the lead time of materials # 读取各个原材料的历史平均交货周期 bom table self.xv_ary_lead_time = xv_ary_bom[:, (1, 4)] # 每一种原材料的到货时间(有重复) # 切换成原材料 self.ev_ary_is_order_material = np.array([False for i in range(xv_material_num)]) # 是否订购原材料 self.ev_ary_num_material_to_order = np.zeros((xv_material_num,)) # 原材料订货数量 self.ev_ary_material_state_to_use = np.zeros((xv_material_num,)) # 一个周期内按照设定生产状态完全生产 原材料消耗数量 计划 self.ev_ary_material_to_use = np.zeros((xv_material_num,)) # 当期实际消耗的原材料数量 self.xv_ary_material = xv_ary_material_id # 原材料顺序 self.xv_ary_bom = xv_ary_bom # bom表 self.xv_ary_plan = xv_ary_plan # plan表 self.ev_lst_trans_quan_material = [0 for i in range(xv_material_num)] # Iss传递给Pss的原材料数量 self.ev_lst_backtrans_quan_material = [0 for i in range(xv_material_num)] # Pss退回的原材料数量 self.ev_ary_order_time = np.zeros((xv_material_num,)) # 原材料订货时间戳 self.ev_ary_arrive_time = np.zeros((xv_material_num,)) # 原材料到货时间戳 # def material_state_to_use(self, ev_int_produce_type, xv_plan_excel): # # 读取Oss决定的生产状态,根据生产状态所需的原材料进行汇总 # # self. ev_ary_material_state_to_use = np.multiply(self.xv_array_dlv_product, 原材料表 ) # produce_state = ev_int_produce_type # 获取生产状态 def material_state_to_use(self): # 根据生产状态 看生产一个周期需要多少原材料 # 读取Oss决定的生产状态,根据生产状态所需的原材料进行汇总 # self. ev_ary_material_state_to_use = np.multiply(self.xv_array_dlv_product, 原材料表 ) produce_state = self.model.the_firm.the_os.ev_int_produce_type # 获取生产状态 produce_plan = self.xv_ary_plan[self.xv_ary_plan[:, 0] == produce_state] # 该生产状态下各产品的生产计划 for product_plan in produce_plan: for bom in self.xv_ary_bom: if product_plan[1] == bom[0]: self.ev_ary_material_state_to_use[np.where(self.xv_ary_material == bom[1])] += float( product_plan[3]) * \ float(bom[ 2]) # 某原材料的生产数量加等产品生产量乘单位原材料消耗量 def material_check(self): # 检查库存是否充足 # 根据Iss决策,核对库存是否充足,并将拥有的原材料交给Pss # 可能需要一部生成原材料列表在调用 # Check whether materials are enough and transfer material # print(len(self.ev_ary_current_material), self.xv_material_num) # print(self.ev_ary_current_material[0, 1]) for i in range(self.xv_material_num): self.ev_lst_trans_quan_material[i] = float(min(float(self.ev_ary_current_material[i, 1]), self.ev_ary_material_state_to_use[i])) # 需要数量和库存两者间的较小值 # if self.ev_ary_current_material[i, 1] >= ev_ary_material_state_to_use[i]: # 库存足够按照计划生产 # self.ev_lst_trans_quan_material[i] = ev_ary_material_state_to_use[i] # else: # self.ev_lst_trans_quan_material[i] = self.ev_ary_current_material[i] # print(type(self.ev_lst_trans_quan_material[i])) def consume_and_store(self, ev_ary_produced_num, ev_changed_product, ev_lst_backtrans_material): self.ev_lst_backtrans_quan_material = ev_lst_backtrans_material # Pss传回的原材料数量 # Update the inventory after production for i in range(self.xv_material_num): self.ev_ary_material_to_use[i] = self.ev_lst_trans_quan_material[i] - \ self.ev_lst_backtrans_quan_material[i] if self.ev_ary_arrive_time[i] == self.model.t: # 判断材料是否到达 self.ev_ary_current_material[i, 1] = float(self.ev_ary_current_material[i, 1]) - self.ev_ary_material_to_use[i] \ + self.ev_ary_num_material_to_order[i] # 减消耗量 加订购量 self.ev_ary_num_material_to_order[i] = 0 self.ev_ary_is_order_material[i] = False self.ev_ary_current_product[:, 1] = ev_changed_product + np.array([float(x) for x in ev_ary_produced_num[:, 1]]) # 上期期末加本期生产 # return self.ev_ary_current_material, self.ev_ary_current_product def material_replenishment(self, xv_ary_s, xv_ary_S): # Check the inventory of material to decide whether to replenish # 核对原材料数量是否低于s # 带时间戳 for i in range(self.xv_material_num): if self.ev_ary_current_material[i, 1] <= xv_ary_s[i, 1] and self.ev_ary_is_order_material[i] == False: self.ev_ary_is_order_material[i] = True self.ev_ary_num_material_to_order[i] = float(xv_ary_S[i, 1]) - float(self.ev_ary_current_material[i, 1]) self.ev_ary_order_time[i] = self.model.t self.ev_ary_arrive_time[i] = self.ev_ary_order_time[i] + float(self.xv_ary_lead_time[ self.xv_ary_lead_time[:, 0] == self.ev_ary_current_material[i, 0]][0, 1]) else: self.ev_ary_num_material_to_order[i] = 0