Coverage for examples/controller/pid_with_simulator.py: 79%
39 statements
« prev ^ index » next coverage.py v7.4.4, created at 2025-10-30 13:39 +0000
« prev ^ index » next coverage.py v7.4.4, created at 2025-10-30 13:39 +0000
1"""A typical example for how to use the AgentLib, requiring only the basic dependencies.
3This example will teach you about:
41. Pre-implemented Modules: Simulator, PID, local communicator
52. How to write a simple dependency free model
63. How to use the alias of variables to facilitate communication between agents
74. How to run agents without the LocalMAS utility
85. How to log and plot the state of an agent using the agentlogger
10"""
12import logging
13from typing import List
15import agentlib as ag
18class HeatedRoomConfig(ag.ModelConfig):
19 inputs: List[ag.ModelInput] = [
20 ag.ModelInput(name="heating_power_in_watt", value=100)
21 ]
22 states: List[ag.ModelState] = [
23 ag.ModelState(name="temperature_in_celsius", value=20)
24 ]
25 parameters: List[ag.ModelParameter] = [
26 ag.ModelParameter(name="heat_loss_in_watt", value=150),
27 ag.ModelParameter(name="thermal_capacity_zone", value=100_000),
28 ]
31class HeatedRoom(ag.Model):
32 config: HeatedRoomConfig
34 def initialize(self, **kwargs):
35 pass
37 def do_step(self, *, t_start, t_sample):
38 t = self.get("temperature_in_celsius").value
39 power = self.get("heating_power_in_watt").value
40 loss = self.get("heat_loss_in_watt").value
41 capacity = self.get("thermal_capacity_zone").value
42 t = t + ((power - loss) / capacity) * t_sample
43 self.set("temperature_in_celsius", t)
46pid_agent_config = {
47 "id": "PID",
48 "modules": [
49 {
50 "module_id": "myPid",
51 "type": "pid",
52 "setpoint": 21,
53 "Kp": 1000,
54 "Ti": 10,
55 "lb": 0,
56 "ub": 500,
57 "input": {"name": "u", "value": 0, "alias": "room_temp"},
58 "output": {
59 "name": "y",
60 "value": 0,
61 "alias": "heating_power",
62 "shared": True,
63 },
64 },
65 {"module_id": "myLogger", "type": "AgentLogger"},
66 {"module_id": "myComm", "type": "local", "subscriptions": ["Process"]},
67 ],
68}
70process_agent_config = {
71 "id": "Process",
72 "modules": [
73 {
74 "module_id": "sim",
75 "type": "simulator",
76 "model": {"type": {"file": __file__, "class_name": "HeatedRoom"}},
77 "t_sample": 10,
78 "inputs": [
79 {"name": "heating_power_in_watt", "value": 0, "alias": "heating_power"}
80 ],
81 "states": [
82 {
83 "name": "temperature_in_celsius",
84 "value": 21,
85 "shared": True,
86 "alias": "room_temp",
87 }
88 ],
89 },
90 {"module_id": "myLogger", "type": "AgentLogger"},
91 {"module_id": "myComm", "type": "local", "subscriptions": ["PID"]},
92 ],
93}
96def run_example(with_plots=True, log_level=logging.INFO):
97 # Set the log-level
98 logging.basicConfig(level=log_level)
100 env_config = {"rt": False, "factor": 0.01, "clock": True, "t_sample": 60}
101 env = ag.Environment(config=env_config)
102 pid_agent = ag.Agent(config=pid_agent_config, env=env)
103 process_agent = ag.Agent(config=process_agent_config, env=env)
104 env.run(until=1000)
106 results = process_agent.get_results()
107 res = results["myLogger"]
108 if with_plots:
109 import matplotlib.pyplot as plt
111 fig, ax = plt.subplots(2, 1)
112 res["room_temp"].plot(ax=ax[0], label="$T_{room}$")
113 ax[0].axhline(21, label="$T_{room, set}$", linestyle="--", color="black")
114 res["heating_power"].plot(ax=ax[1], label="$\dot{Q}_{heat}$")
115 ax[0].legend()
116 ax[1].legend()
117 plt.show()
118 return {"PID_1": results}
121if __name__ == "__main__":
122 run_example(log_level="INFO")