Now you are the thermostat. A hidden room is simulated minute by minute for 12 hours, and every minute the simulator calls your function
controller(temperature, setpoint, heater_on) -> bool
with the thermometer's reading (°C), the desired temperature, and whether the 3 kW heater is on right now. Return True to have the heater on for the next minute and False to have it off.
What you are up against:
- the room leaks heat to the outside with a time constant of 100 minutes, or 60 minutes while a window is open (two to four times a day, for 5 to 25 minutes);
- the outside temperature drifts slowly over the day, somewhere between about −1 and 12 °C;
- the heater lags: its output takes about 3 minutes to rise after you switch it on and to die away after you switch it off, so the room keeps warming for a while after you turn it off;
- the thermometer is noisy: each reading is the true temperature plus a random error of a few hundredths of a degree, rounded to 0.01 °C;
- the room starts cold, so the first 90 minutes are a warm-up that is not judged.
Each test calls run_room(controller, seed) (it is defined for you, so you can try it with Run), which returns a summary of the 630 judged minutes, for example
{"setpoint": 19.5, "minutes_outside_band": 0, "rms_error": 0.094933,
"switches_per_hour": 27.238095, "worst_error": 0.2957}
for the naive lambda temperature, setpoint, heater_on: temperature < setpoint on seed 1. Your function may remember values between calls in a global variable (for example the previous reading); run_room gives no signal when a new room starts, so make sure stale values only matter for a minute or two.
How this problem is scored
- A test passes when the room stays within
setpoint ± 1°C for every judged minute. - Its quality is
100 - 100 * rms_error - 2 * switches_per_hour(at least 0), whererms_erroris the root-mean-square difference between the room and the setpoint over the judged minutes: every 0.1 °C of typical error costs 10 points, and every switch per hour costs 2 points, for the wear it puts on the heater. - The naive controller above passes seed 1 but scores only 36: the noise makes it switch 27 times an hour. Comfort and few switches pull in opposite directions; the best controllers find a good balance.
Constraints
- return a
bool(or a value that is clearly true or false);Nonecounts as off - the result must not depend on the clock; each call should take well under a millisecond
Goals
- Write a feedback controller that is called once per time step by a simulator
- Keep a room inside a comfort band despite noise, lag, open windows and changing weather
- Balance comfort against wear on the heater