Skip to content

[BUG] DHW Storage is never used #156

@LorenzoBonanni

Description

@LorenzoBonanni

Issue Description

There is an incorrect variable reference in citylearn/building.py that prevents the Domestic Hot Water (DHW) storage system from updating its state of charge or energy balance. DHW actions are multiplied by self.heating_storage.capacity instead of self.dhw_storage.capacity.

When heating_storage is disabled (as in the 2023 challenge dataset), heating_storage.capacity == 0, causing DHW storage to remain unused even though dhw_storage appears as an active action.

Expected Behavior

When the agent outputs non-zero dhw_storage actions, the DHW tank should charge or discharge according to its configured capacity. Its SOC and energy balance should vary over time.

Actual Behavior

  • dhw_storage actions have no effect.
  • DHW SOC stays strictly zero for the entire episode.
  • DHW energy balance remains zero.
  • All DHW demand is supplied directly by the electric heater.
  • Changing one line of code to reference self.dhw_storage.capacity produces
    the expected non-zero behavior.

Output with original code (incorrect)


DHW Storage SOC: [0. 0. 0. 0. ... 0.]

Output after fixing the line


DHW Storage SOC: [0.9780134 1. 1. 1. ... 0.62974083 1. 0.]

This clearly shows that DHW storage behavior is completely suppressed in the current version.

Steps to Reproduce

  1. Use the citylearn_challenge_2023_phase_1 dataset where:

    • dhw_storage is active,
    • heating_storage is inactive → capacity = 0.
  2. Create any agent that outputs non-zero dhw_storage actions.

  3. Run a full episode and log:

    • env.buildings[0].dhw_storage.soc
  4. Observe that SOC stays zero throughout the entire simulation.

Minimal Reproducible Example

from typing import List
from citylearn.agents.base import Agent
from citylearn.citylearn import CityLearnEnv

class CustomRBC(Agent):
    def __init__(self, env: CityLearnEnv, **kwargs):
        super().__init__(env, **kwargs)

    def predict(self, observations: List[List[float]], deterministic=True):
        actions = []
        for i, o in enumerate(observations):
            available_obs = self.observation_names[i]
            available_act = self.action_names[i]
            action = [0.0 for _ in range(len(available_act))]
            hour = o[available_obs.index('hour')]

            if 'dhw_storage' in available_act:
                if 6 <= hour <= 9 or 18 <= hour <= 22:
                    action[available_act.index('dhw_storage')] = -0.2
                else:
                    action[available_act.index('dhw_storage')] = 1.0

            actions.append(action)
        return actions

env = CityLearnEnv(
    schema='citylearn_challenge_2023_phase_1',
    central_agent=True,
)

agent = CustomRBC(env)

obs, _ = env.reset(seed=0)
while not env.terminated:
    action = agent.predict(obs)
    obs, reward, _, _, _ = env.step(action)

print("DHW Storage SOC:", env.buildings[0].dhw_storage.soc)

Environment

  • CityLearn version: 2.4.2
  • Dataset: citylearn_challenge_2023_phase_1
  • Operating System: Ubuntu 24.04
  • Python version: 3.10.19
  • Issue present also in latest main branch at time of reporting.

Root Cause

In building.py around line 1765:

energy = action * self.heating_storage.capacity * self.algorithm_action_based_time_step_hours_ratio

This uses the heating storage capacity even when processing DHW actions.

Possible Solution

Replace the incorrect line with:

energy = action * self.dhw_storage.capacity * self.algorithm_action_based_time_step_hours_ratio

This immediately restores correct DHW storage behavior.

Additional Notes

This bug makes DHW storage unusable in all configurations where heating storage is inactive (capacity = 0), including the official challenge dataset. Fixing it is necessary for agents to learn or implement any DHW shifting strategies.

Metadata

Metadata

Assignees

Labels

bugSomething isn't working

Type

No type

Projects

No projects

Milestone

No milestone

Relationships

None yet

Development

No branches or pull requests

Issue actions