Commit Β·
0954bcf
1
Parent(s): 9cdea7c
Raise treatment reduction, lower medium/hard seeds, focus prompt strategy
Browse files- baseline/policy.py +5 -4
- server/constants.py +1 -1
- server/tasks/task_hard.py +20 -26
- server/tasks/task_medium.py +13 -18
baseline/policy.py
CHANGED
|
@@ -69,8 +69,8 @@ def build_prompt(obs: CityObservation) -> str:
|
|
| 69 |
"",
|
| 70 |
"DECISION RULES (follow in order):",
|
| 71 |
"1. If ANY hospital is below 0.3 capacity: 'allocate' on that district IMMEDIATELY.",
|
| 72 |
-
"2. If resources > 0
|
| 73 |
-
"3.
|
| 74 |
"4. If resources = 0: 'restrict' on the highest infected district.",
|
| 75 |
"5. NEVER use 'test' β data is already accurate.",
|
| 76 |
"6. NEVER restrict a SAFE district (below 0.2) β you will be penalised.",
|
|
@@ -86,8 +86,9 @@ def build_prompt(obs: CityObservation) -> str:
|
|
| 86 |
"DECISION RULES (follow in order):",
|
| 87 |
"1. If ANY hospital is below 0.3 capacity: 'allocate' on that district IMMEDIATELY.",
|
| 88 |
"2. If resources > 0: 'allocate' on the district with HIGHEST growth_hint.",
|
| 89 |
-
"3.
|
| 90 |
-
"4.
|
|
|
|
| 91 |
]
|
| 92 |
|
| 93 |
lines += [
|
|
|
|
| 69 |
"",
|
| 70 |
"DECISION RULES (follow in order):",
|
| 71 |
"1. If ANY hospital is below 0.3 capacity: 'allocate' on that district IMMEDIATELY.",
|
| 72 |
+
"2. If resources > 0: ALWAYS 'allocate' on the district with the SINGLE HIGHEST infection rate.",
|
| 73 |
+
"3. Do NOT spread resources across multiple districts in the same turn β focus all pressure on the worst district.",
|
| 74 |
"4. If resources = 0: 'restrict' on the highest infected district.",
|
| 75 |
"5. NEVER use 'test' β data is already accurate.",
|
| 76 |
"6. NEVER restrict a SAFE district (below 0.2) β you will be penalised.",
|
|
|
|
| 86 |
"DECISION RULES (follow in order):",
|
| 87 |
"1. If ANY hospital is below 0.3 capacity: 'allocate' on that district IMMEDIATELY.",
|
| 88 |
"2. If resources > 0: 'allocate' on the district with HIGHEST growth_hint.",
|
| 89 |
+
"3. Sustain pressure β keep allocating to the same district until growth_hint drops below 0.08.",
|
| 90 |
+
"4. If resources = 0: 'restrict' on highest growth_hint district.",
|
| 91 |
+
"5. NEVER use 'test'.",
|
| 92 |
]
|
| 93 |
|
| 94 |
lines += [
|
server/constants.py
CHANGED
|
@@ -46,7 +46,7 @@ SPREAD_RATE_MIN = 0.05 # Slowest possible spread rate per day
|
|
| 46 |
SPREAD_RATE_MAX = 0.13 # Fastest possible spread rate per day
|
| 47 |
GROWTH_HINT_NOISE = 0.03 # Noise on growth_rate_hint (Β± value)
|
| 48 |
|
| 49 |
-
TREATMENT_REDUCTION = 0.
|
| 50 |
ALLOCATE_REDUCTION = 0.10 # Allocating reduces future spread rate this step
|
| 51 |
RESTRICT_REDUCTION = 0.05 # Restricting reduces spread per step
|
| 52 |
SPILLOVER_RATE = 0.01 # Infection fraction that spills to adjacent districts
|
|
|
|
| 46 |
SPREAD_RATE_MAX = 0.13 # Fastest possible spread rate per day
|
| 47 |
GROWTH_HINT_NOISE = 0.03 # Noise on growth_rate_hint (Β± value)
|
| 48 |
|
| 49 |
+
TREATMENT_REDUCTION = 0.10 # Allocating reduces existing infection this step
|
| 50 |
ALLOCATE_REDUCTION = 0.10 # Allocating reduces future spread rate this step
|
| 51 |
RESTRICT_REDUCTION = 0.05 # Restricting reduces spread per step
|
| 52 |
SPILLOVER_RATE = 0.01 # Infection fraction that spills to adjacent districts
|
server/tasks/task_hard.py
CHANGED
|
@@ -1,15 +1,8 @@
|
|
| 1 |
# server/tasks/task_hard.py
|
| 2 |
-
# βββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ
|
| 3 |
-
# Hard task: 6 districts, 3-day data lag, scarce resources.
|
| 4 |
-
# All districts start with small but growing infections.
|
| 5 |
-
# Agent must learn to read growth_rate_hint signals and act proactively
|
| 6 |
-
# on districts that look manageable today but will be critical in 3 days.
|
| 7 |
-
# βββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ
|
| 8 |
-
|
| 9 |
import sys
|
| 10 |
import os
|
| 11 |
-
sys.path.insert(0, os.path.join(os.path.dirname(__file__), '..'))
|
| 12 |
-
sys.path.insert(0, os.path.join(os.path.dirname(__file__), '../..'))
|
| 13 |
|
| 14 |
from models import CityState
|
| 15 |
from server.utils import generate_districts
|
|
@@ -20,24 +13,25 @@ from server.constants import TASK_CONFIG
|
|
| 20 |
class HardTask(BaseTask):
|
| 21 |
|
| 22 |
name = "hard"
|
| 23 |
-
num_districts = TASK_CONFIG["hard"]["num_districts"]
|
| 24 |
-
max_steps = TASK_CONFIG["hard"]["max_steps"]
|
| 25 |
-
resource_pool = TASK_CONFIG["hard"]["resource_pool"]
|
| 26 |
-
data_lag_days = TASK_CONFIG["hard"]["data_lag_days"]
|
| 27 |
|
| 28 |
def build_initial_state(self) -> CityState:
|
| 29 |
-
# All districts start with small
|
| 30 |
-
# The 3-day lag means
|
| 31 |
-
#
|
| 32 |
-
|
| 33 |
-
|
| 34 |
-
#
|
| 35 |
-
|
| 36 |
-
|
|
|
|
| 37 |
infection_history = [
|
| 38 |
-
initial_rates[:],
|
| 39 |
-
initial_rates[:],
|
| 40 |
-
initial_rates[:],
|
| 41 |
]
|
| 42 |
|
| 43 |
return CityState(
|
|
@@ -47,8 +41,8 @@ class HardTask(BaseTask):
|
|
| 47 |
data_lag_days = self.data_lag_days,
|
| 48 |
max_steps = self.max_steps,
|
| 49 |
districts = generate_districts(
|
| 50 |
-
num_districts
|
| 51 |
-
seed_infections
|
| 52 |
),
|
| 53 |
infection_history = infection_history,
|
| 54 |
)
|
|
|
|
| 1 |
# server/tasks/task_hard.py
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 2 |
import sys
|
| 3 |
import os
|
| 4 |
+
sys.path.insert(0, os.path.join(os.path.dirname(__file__), '..'))
|
| 5 |
+
sys.path.insert(0, os.path.join(os.path.dirname(__file__), '../..'))
|
| 6 |
|
| 7 |
from models import CityState
|
| 8 |
from server.utils import generate_districts
|
|
|
|
| 13 |
class HardTask(BaseTask):
|
| 14 |
|
| 15 |
name = "hard"
|
| 16 |
+
num_districts = TASK_CONFIG["hard"]["num_districts"]
|
| 17 |
+
max_steps = TASK_CONFIG["hard"]["max_steps"]
|
| 18 |
+
resource_pool = TASK_CONFIG["hard"]["resource_pool"]
|
| 19 |
+
data_lag_days = TASK_CONFIG["hard"]["data_lag_days"]
|
| 20 |
|
| 21 |
def build_initial_state(self) -> CityState:
|
| 22 |
+
# All districts start with small but growing infections.
|
| 23 |
+
# The 3-day lag means agent sees these seed values while true
|
| 24 |
+
# infection is already 3 days ahead β districts D0, D2, D4 will
|
| 25 |
+
# be CRITICAL before the agent sees updated data.
|
| 26 |
+
# 7 resources for 6 districts with delayed information is
|
| 27 |
+
# the hardest possible triage scenario.
|
| 28 |
+
seed_infections = [0.10, 0.06, 0.12, 0.05, 0.13, 0.07]
|
| 29 |
+
|
| 30 |
+
initial_rates = seed_infections[:]
|
| 31 |
infection_history = [
|
| 32 |
+
initial_rates[:], # day -3 (what agent sees on step 1)
|
| 33 |
+
initial_rates[:], # day -2
|
| 34 |
+
initial_rates[:], # day -1
|
| 35 |
]
|
| 36 |
|
| 37 |
return CityState(
|
|
|
|
| 41 |
data_lag_days = self.data_lag_days,
|
| 42 |
max_steps = self.max_steps,
|
| 43 |
districts = generate_districts(
|
| 44 |
+
num_districts = self.num_districts,
|
| 45 |
+
seed_infections = seed_infections,
|
| 46 |
),
|
| 47 |
infection_history = infection_history,
|
| 48 |
)
|
server/tasks/task_medium.py
CHANGED
|
@@ -1,14 +1,8 @@
|
|
| 1 |
# server/tasks/task_medium.py
|
| 2 |
-
# βββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ
|
| 3 |
-
# Medium task: 4 districts, 2 simultaneous outbreaks, tighter resource pool.
|
| 4 |
-
# Agent must prioritise between competing threats β it cannot fully
|
| 5 |
-
# address both outbreaks simultaneously and must learn to triage.
|
| 6 |
-
# βββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ
|
| 7 |
-
|
| 8 |
import sys
|
| 9 |
import os
|
| 10 |
-
sys.path.insert(0, os.path.join(os.path.dirname(__file__), '..'))
|
| 11 |
-
sys.path.insert(0, os.path.join(os.path.dirname(__file__), '../..'))
|
| 12 |
|
| 13 |
from models import CityState
|
| 14 |
from server.utils import generate_districts
|
|
@@ -19,16 +13,17 @@ from server.constants import TASK_CONFIG
|
|
| 19 |
class MediumTask(BaseTask):
|
| 20 |
|
| 21 |
name = "medium"
|
| 22 |
-
num_districts = TASK_CONFIG["medium"]["num_districts"]
|
| 23 |
-
max_steps = TASK_CONFIG["medium"]["max_steps"]
|
| 24 |
-
resource_pool = TASK_CONFIG["medium"]["resource_pool"]
|
| 25 |
-
data_lag_days = TASK_CONFIG["medium"]["data_lag_days"]
|
| 26 |
|
| 27 |
def build_initial_state(self) -> CityState:
|
| 28 |
-
#
|
| 29 |
-
#
|
| 30 |
-
#
|
| 31 |
-
|
|
|
|
| 32 |
|
| 33 |
return CityState(
|
| 34 |
day = 0,
|
|
@@ -37,8 +32,8 @@ class MediumTask(BaseTask):
|
|
| 37 |
data_lag_days = self.data_lag_days,
|
| 38 |
max_steps = self.max_steps,
|
| 39 |
districts = generate_districts(
|
| 40 |
-
num_districts
|
| 41 |
-
seed_infections
|
| 42 |
),
|
| 43 |
infection_history = [],
|
| 44 |
)
|
|
|
|
| 1 |
# server/tasks/task_medium.py
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 2 |
import sys
|
| 3 |
import os
|
| 4 |
+
sys.path.insert(0, os.path.join(os.path.dirname(__file__), '..'))
|
| 5 |
+
sys.path.insert(0, os.path.join(os.path.dirname(__file__), '../..'))
|
| 6 |
|
| 7 |
from models import CityState
|
| 8 |
from server.utils import generate_districts
|
|
|
|
| 13 |
class MediumTask(BaseTask):
|
| 14 |
|
| 15 |
name = "medium"
|
| 16 |
+
num_districts = TASK_CONFIG["medium"]["num_districts"]
|
| 17 |
+
max_steps = TASK_CONFIG["medium"]["max_steps"]
|
| 18 |
+
resource_pool = TASK_CONFIG["medium"]["resource_pool"]
|
| 19 |
+
data_lag_days = TASK_CONFIG["medium"]["data_lag_days"]
|
| 20 |
|
| 21 |
def build_initial_state(self) -> CityState:
|
| 22 |
+
# D0 and D2 seeded with outbreaks (non-adjacent).
|
| 23 |
+
# D1 and D3 start clean but will grow into critical within 3-4 steps.
|
| 24 |
+
# 8 total resources for 4 districts creates genuine triage pressure β
|
| 25 |
+
# agent cannot save all districts and must choose strategically.
|
| 26 |
+
seed_infections = [0.18, 0.03, 0.15, 0.03]
|
| 27 |
|
| 28 |
return CityState(
|
| 29 |
day = 0,
|
|
|
|
| 32 |
data_lag_days = self.data_lag_days,
|
| 33 |
max_steps = self.max_steps,
|
| 34 |
districts = generate_districts(
|
| 35 |
+
num_districts = self.num_districts,
|
| 36 |
+
seed_infections = seed_infections,
|
| 37 |
),
|
| 38 |
infection_history = [],
|
| 39 |
)
|