18. Basic example

Sinergym utilizes the standard Farama Gymnasium API. Let’s explore how to create a basic loop.

To begin, we need to import Sinergym and create an environment. In this example, we will use the Eplus-demo-v1 environment.

[1]:
import gymnasium as gym
import numpy as np

import sinergym
env = gym.make('Eplus-demo-v1')
#==============================================================================================#
[ENVIRONMENT] (INFO) : Creating Gymnasium environment... [demo-v1]
#==============================================================================================#
[MODELING] (INFO) : Experiment working directory created [/workspaces/sinergym/examples/Eplus-env-demo-v1-res1]
[MODELING] (INFO) : Model Config is correct.
[MODELING] (INFO) : Updated building model with whole Output:Variable available names
[MODELING] (INFO) : Updated building model with whole Output:Meter available names
[MODELING] (INFO) : Extra config: runperiod updated to {'apply_weekend_holiday_rule': 'No', 'begin_day_of_month': 1, 'begin_month': 1, 'begin_year': 1991, 'day_of_week_for_start_day': 'Monday', 'end_day_of_month': 1, 'end_month': 3, 'end_year': 1991, 'use_weather_file_daylight_saving_period': 'Yes', 'use_weather_file_holidays_and_special_days': 'Yes', 'use_weather_file_rain_indicators': 'Yes', 'use_weather_file_snow_indicators': 'Yes'}
[MODELING] (INFO) : Updated episode length (seconds): 5184000.0
[MODELING] (INFO) : Updated timestep size (seconds): 3600.0
[MODELING] (INFO) : Updated timesteps per episode: 1440
[MODELING] (INFO) : runperiod established: {'start_day': 1, 'start_month': 1, 'start_year': 1991, 'end_day': 1, 'end_month': 3, 'end_year': 1991, 'start_weekday': 0, 'n_steps_per_hour': 1}
[MODELING] (INFO) : Episode length (seconds): 5184000.0
[MODELING] (INFO) : timestep size (seconds): 3600.0
[MODELING] (INFO) : timesteps per episode: 1441
[REWARD] (INFO) : Reward function initialized.
[ENVIRONMENT] (INFO) : Environment demo-v1 created successfully.

At first glance, Sinergym might seem to be only imported and not used. However, importing Sinergym inherently defines all its Environments for use. In this instance, Eplus-demo-v1 is readily available with all its features.

With this straightforward setup, we’re prepared to iterate over the episodes. For this basic example, we’ll consider just one episode. Essentially, the required code would look something like this:

[2]:
for i in range(1):
    obs, info = env.reset()
    rewards = []
    truncated = terminated = False
    current_month = 0
    while not (terminated or truncated):
        a = env.action_space.sample()
        obs, reward, terminated, truncated, info = env.step(a)
        rewards.append(reward)
        if info['month'] != current_month:  # display results every month
            current_month = info['month']
            print('Reward: ', sum(rewards), info)
#----------------------------------------------------------------------------------------------#
[ENVIRONMENT] (INFO) : Starting a new episode... [demo-v1] [Episode 1]
#----------------------------------------------------------------------------------------------#
[MODELING] (INFO) : Episode directory created [/workspaces/sinergym/examples/Eplus-env-demo-v1-res1/Eplus-env-sub_run1]
[MODELING] (INFO) : Weather file USA_PA_Pittsburgh-Allegheny.County.AP.725205_TMY3.epw used.
[MODELING] (INFO) : Adapting weather to building model. [USA_PA_Pittsburgh-Allegheny.County.AP.725205_TMY3.epw]
[ENVIRONMENT] (INFO) : Saving episode output path... [/workspaces/sinergym/examples/Eplus-env-demo-v1-res1/Eplus-env-sub_run1/output]
/usr/local/lib/python3.12/dist-packages/opyplus/weather_data/weather_data.py:485: FutureWarning: Downcasting behavior in `replace` is deprecated and will be removed in a future version. To retain the old behavior, explicitly call `result.infer_objects(copy=False)`. To opt-in to the future behavior, set `pd.set_option('future.no_silent_downcasting', True)`
  df = df.replace(
[SIMULATOR] (INFO) : Running EnergyPlus with args: ['-w', '/workspaces/sinergym/examples/Eplus-env-demo-v1-res1/Eplus-env-sub_run1/USA_PA_Pittsburgh-Allegheny.County.AP.725205_TMY3.epw', '-d', '/workspaces/sinergym/examples/Eplus-env-demo-v1-res1/Eplus-env-sub_run1/output', '/workspaces/sinergym/examples/Eplus-env-demo-v1-res1/Eplus-env-sub_run1/5ZoneAutoDXVAV.epJSON']
[ENVIRONMENT] (INFO) : Episode 1 started.
[SIMULATOR] (INFO) : handlers initialized.
[SIMULATOR] (INFO) : handlers are ready.
[SIMULATOR] (INFO) : System is ready.
Reward:  -43.96143518328036 {'time_elapsed(hours)': 2.5, 'month': 1, 'day': 1, 'hour': 1, 'is_raining': False, 'action': array([18.127132, 29.879616], dtype=float32), 'timestep': 2, 'reward': -43.96143518328036, 'energy_term': -43.67932315835093, 'comfort_term': -0.2821120249294271, 'reward_weight': 0.5, 'abs_energy_penalty': -87.35864631670186, 'abs_comfort_penalty': -0.5642240498588542, 'total_power_demand': 87.35864631670186, 'total_temperature_violation': 0.5642240498588542}
Reward:  -1647249.5548937914 {'time_elapsed(hours)': 745.1666666666666, 'month': 2, 'day': 1, 'hour': 0, 'is_raining': False, 'action': array([16.656622, 24.757486], dtype=float32), 'timestep': 745, 'reward': -1143.0965216209067, 'energy_term': -1142.8331083528346, 'comfort_term': -0.26341326807199295, 'reward_weight': 0.5, 'abs_energy_penalty': -2285.6662167056693, 'abs_comfort_penalty': -0.5268265361439859, 'total_power_demand': 2285.6662167056693, 'total_temperature_violation': 0.5268265361439859}
Reward:  -2823733.660524665 {'time_elapsed(hours)': 1417.3333333333333, 'month': 3, 'day': 1, 'hour': 0, 'is_raining': False, 'action': array([22.073221, 22.731335], dtype=float32), 'timestep': 1417, 'reward': -77.46907752986611, 'energy_term': -77.46907752986611, 'comfort_term': 0.0, 'reward_weight': 0.5, 'abs_energy_penalty': -154.93815505973222, 'abs_comfort_penalty': 0, 'total_power_demand': 154.93815505973222, 'total_temperature_violation': 0.0}

As always, remember to close the environment once the interaction is complete:

[3]:
env.close()
[ENVIRONMENT] (INFO) : Environment closed. [demo-v1]

Now, let’s examine the final rewards:

[4]:
print(
    'Mean reward: ',
    np.mean(rewards),
    'Cumulative reward: ',
    sum(rewards))
Mean reward:  -1968.779798007256 Cumulative reward:  -2835042.9091304485

Sinergym has an extensive list of registered environments. We utilize building files with varying characteristics, such as continuous or discrete action spaces, different weather types, weather noise, run periods, timesteps, reward functions, and more. We’ll explore these in the upcoming notebooks.