Lilli98 commited on
Commit
eaa9a52
·
verified ·
1 Parent(s): 5d0fe47

Update app.py

Browse files
Files changed (1) hide show
  1. app.py +28 -10
app.py CHANGED
@@ -26,10 +26,16 @@ from huggingface_hub import upload_file, HfApi
26
  # CONFIG
27
  # ---------------------------
28
  DEFAULT_WEEKS = 36 # 24 或 36 可选,默认 36
29
- TRANSPORT_DELAY = 2
 
 
 
 
 
30
  INITIAL_INVENTORY = 12
31
  INITIAL_BACKLOG = 0
32
 
 
33
  OPENAI_MODEL = "gpt-4o-mini"
34
 
35
  LOCAL_LOG_DIR = Path("logs")
@@ -82,15 +88,15 @@ def ensure_state_compat(state: dict):
82
  state.setdefault("inventory", {r: INITIAL_INVENTORY for r in roles})
83
  state.setdefault("backlog", {r: INITIAL_BACKLOG for r in roles})
84
 
85
- # pipeline: ensure lists and proper length >= TRANSPORT_DELAY
86
  if "pipeline" not in state:
87
- state["pipeline"] = {r: [0] * TRANSPORT_DELAY for r in roles}
88
  else:
89
  for r in roles:
90
- state["pipeline"].setdefault(r, [0] * TRANSPORT_DELAY)
91
- # pad if shorter than TRANSPORT_DELAY
92
- if len(state["pipeline"][r]) < TRANSPORT_DELAY:
93
- state["pipeline"][r] = state["pipeline"][r] + [0] * (TRANSPORT_DELAY - len(state["pipeline"][r]))
94
 
95
  # incoming_orders, orders_history, shipments_history
96
  state.setdefault("incoming_orders", {r: 0 for r in roles})
@@ -192,7 +198,7 @@ def init_game(weeks=DEFAULT_WEEKS):
192
  "roles": roles,
193
  "inventory": {r: INITIAL_INVENTORY for r in roles},
194
  "backlog": {r: INITIAL_BACKLOG for r in roles},
195
- "pipeline": {r: [0] * TRANSPORT_DELAY for r in roles},
196
  "incoming_orders": {r: 0 for r in roles},
197
  "orders_history": {r: [] for r in roles},
198
  "shipments_history": {r: [] for r in roles},
@@ -277,7 +283,7 @@ def step_game(state: dict, distributor_order: int):
277
  elif role == "wholesaler":
278
  state["incoming_orders"]["factory"] = order_val
279
 
280
- # 6) place orders into pipelines (will arrive after TRANSPORT_DELAY)
281
  downstream_map = {"factory": "wholesaler", "wholesaler": "distributor", "distributor": "retailer", "retailer": None}
282
  for role in roles:
283
  placed_order = state["orders_history"][role][-1] if state["orders_history"].get(role) else 0
@@ -285,9 +291,20 @@ def step_game(state: dict, distributor_order: int):
285
  placed_order = int(distributor_order)
286
  downstream = downstream_map.get(role)
287
  if downstream:
288
- state["pipeline"].setdefault(downstream, [0]*TRANSPORT_DELAY)
289
  state["pipeline"][downstream].append(placed_order)
290
 
 
 
 
 
 
 
 
 
 
 
 
291
  # 7) logging
292
  log_entry = {
293
  "timestamp": now_iso(),
@@ -298,6 +315,7 @@ def step_game(state: dict, distributor_order: int):
298
  "orders_submitted": {r: (state["orders_history"].get(r, [None])[-1] if state["orders_history"].get(r) else None) for r in roles},
299
  "inventory": {r: state["inventory"].get(r, 0) for r in roles},
300
  "backlog": {r: state["backlog"].get(r, 0) for r in roles},
 
301
  "info_sharing": state.get("info_sharing", False),
302
  "info_history_weeks": state.get("info_history_weeks", 0),
303
  "llm_raw": {k: v["raw"] for k, v in llm_outputs.items()}
 
26
  # CONFIG
27
  # ---------------------------
28
  DEFAULT_WEEKS = 36 # 24 或 36 可选,默认 36
29
+
30
+ # Lead times
31
+ ORDER_LEAD_TIME = 1 # Time for orders to reach supplier
32
+ SHIPPING_LEAD_TIME = 2 # Time for shipments to arrive
33
+ PRODUCTION_LEAD_TIME = 2 # Time for factory to produce goods
34
+
35
  INITIAL_INVENTORY = 12
36
  INITIAL_BACKLOG = 0
37
 
38
+
39
  OPENAI_MODEL = "gpt-4o-mini"
40
 
41
  LOCAL_LOG_DIR = Path("logs")
 
88
  state.setdefault("inventory", {r: INITIAL_INVENTORY for r in roles})
89
  state.setdefault("backlog", {r: INITIAL_BACKLOG for r in roles})
90
 
91
+ # pipeline: ensure lists and proper length >= SHIPPING_LEAD_TIME
92
  if "pipeline" not in state:
93
+ state["pipeline"] = {r: [4] * SHIPPING_LEAD_TIME for r in roles}
94
  else:
95
  for r in roles:
96
+ state["pipeline"].setdefault(r, [4] * SHIPPING_LEAD_TIME)
97
+ # pad if shorter than SHIPPING_LEAD_TIME
98
+ if len(state["pipeline"][r]) < SHIPPING_LEAD_TIME:
99
+ state["pipeline"][r] = state["pipeline"][r] + [4] * (SHIPPING_LEAD_TIME - len(state["pipeline"][r]))
100
 
101
  # incoming_orders, orders_history, shipments_history
102
  state.setdefault("incoming_orders", {r: 0 for r in roles})
 
198
  "roles": roles,
199
  "inventory": {r: INITIAL_INVENTORY for r in roles},
200
  "backlog": {r: INITIAL_BACKLOG for r in roles},
201
+ "pipeline": {r: [4] * SHIPPING_LEAD_TIME for r in roles},
202
  "incoming_orders": {r: 0 for r in roles},
203
  "orders_history": {r: [] for r in roles},
204
  "shipments_history": {r: [] for r in roles},
 
283
  elif role == "wholesaler":
284
  state["incoming_orders"]["factory"] = order_val
285
 
286
+ # 6) place orders into pipelines (will arrive after SHIPPING_LEAD_TIME)
287
  downstream_map = {"factory": "wholesaler", "wholesaler": "distributor", "distributor": "retailer", "retailer": None}
288
  for role in roles:
289
  placed_order = state["orders_history"][role][-1] if state["orders_history"].get(role) else 0
 
291
  placed_order = int(distributor_order)
292
  downstream = downstream_map.get(role)
293
  if downstream:
294
+ state["pipeline"].setdefault(downstream, [0]*SHIPPING_LEAD_TIME)
295
  state["pipeline"][downstream].append(placed_order)
296
 
297
+ # 6.5) cost calculation
298
+ if "cost" not in state:
299
+ state["cost"] = {r: 0.0 for r in roles}
300
+
301
+ for r in roles:
302
+ inv = state["inventory"].get(r, 0)
303
+ backlog = state["backlog"].get(r, 0)
304
+ inv_cost = inv * 0.5 # 每单位库存成本
305
+ back_cost = backlog * 1.0 # 每单位缺货成本
306
+ state["cost"][r] = state["cost"].get(r, 0) + inv_cost + back_cost
307
+
308
  # 7) logging
309
  log_entry = {
310
  "timestamp": now_iso(),
 
315
  "orders_submitted": {r: (state["orders_history"].get(r, [None])[-1] if state["orders_history"].get(r) else None) for r in roles},
316
  "inventory": {r: state["inventory"].get(r, 0) for r in roles},
317
  "backlog": {r: state["backlog"].get(r, 0) for r in roles},
318
+ "cost": {r: state["cost"].get(r, 0) for r in roles},
319
  "info_sharing": state.get("info_sharing", False),
320
  "info_history_weeks": state.get("info_history_weeks", 0),
321
  "llm_raw": {k: v["raw"] for k, v in llm_outputs.items()}