Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

add renaming of nn to ml #12

Open
wants to merge 22 commits into
base: main
Choose a base branch
from
Open
Show file tree
Hide file tree
Changes from 3 commits
Commits
Show all changes
22 commits
Select commit Hold shift + click to select a range
18764dd
add initial algebraics to casadi_ml.py
SteffenEserAC Sep 20, 2024
43884f4
adjust naming in examples
SteffenEserAC Sep 20, 2024
8b07e54
format with ruff
SteffenEserAC Sep 20, 2024
7c42439
Update agentlib_mpc/optimization_backends/casadi_/casadi_ml.py
EserSteffen Oct 23, 2024
815ab37
Update agentlib_mpc/optimization_backends/casadi_/casadi_ml.py
EserSteffen Oct 23, 2024
e0f9122
uncache result df, as it is mutated during results writing
SteffenEserAC Oct 23, 2024
9479ba6
Merge remote-tracking branch 'origin/11-include-some-updates-from-git…
SteffenEserAC Oct 23, 2024
71b8036
fix space from github
SteffenEserAC Oct 23, 2024
d6b7131
adjust error message
SteffenEserAC Oct 30, 2024
c036dfc
merge main
SteffenEserAC Oct 31, 2024
4970054
dashboard now updates traces synchronously among all plots
SteffenEserAC Nov 7, 2024
d6ff61c
add validation for couplings to have a vlaue for the initial guess
SteffenEserAC Nov 14, 2024
668bf74
make algebraics and outputs inputs for the integrator in mpc
SteffenEserAC Nov 14, 2024
fed6167
remove outputs from initials in discretization and some renaming
SteffenEserAC Nov 14, 2024
557af75
allow algebraics again
SteffenEserAC Nov 14, 2024
a43e975
allow algebraics again
SteffenEserAC Nov 14, 2024
dfa819b
remove superfluous control from ml mpc
SteffenEserAC Nov 14, 2024
7af3bc9
Merge remote-tracking branch 'origin/11-include-some-updates-from-git…
SteffenEserAC Nov 14, 2024
222ce0d
add version number and fix bug
SteffenEserAC Nov 14, 2024
1c3bd51
fix time usage in mpc lags
SteffenEserAC Nov 14, 2024
d247814
add admm dasboard
SteffenEserAC Nov 14, 2024
9031329
Revert "allow algebraics again"
SteffenEserAC Nov 15, 2024
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 0 additions & 2 deletions agentlib_mpc/data_structures/__init__.py
Original file line number Diff line number Diff line change
@@ -1,3 +1 @@



4 changes: 2 additions & 2 deletions agentlib_mpc/data_structures/casadi_utils.py
Original file line number Diff line number Diff line change
Expand Up @@ -247,7 +247,7 @@ def _create_proxqp_solver(self, nlp: dict, options: dict):
"verbose": False,
"print_time": False,
"record_time": True,
"proxqp": {"max_iter": 200, "eps_abs": 1e-4, "backend": "sparse"}
"proxqp": {"max_iter": 200, "eps_abs": 1e-4, "backend": "sparse"},
}
opts = {**default_opts, **options}
return ca.qpsol("mpc", "proxqp", nlp, opts)
Expand All @@ -257,7 +257,7 @@ def _create_osqp_solver(self, nlp: dict, options: dict):
"verbose": False,
"print_time": False,
"record_time": True,
"osqp": {"max_iter": 200, "eps_abs": 1e-4, "verbose": False}
"osqp": {"max_iter": 200, "eps_abs": 1e-4, "verbose": False},
}
opts = {**default_opts, **options}
return ca.qpsol("mpc", "osqp", nlp, opts)
Expand Down
4 changes: 1 addition & 3 deletions agentlib_mpc/data_structures/mpc_datamodels.py
Original file line number Diff line number Diff line change
Expand Up @@ -42,11 +42,9 @@ class DiscretizationOptions(pydantic.BaseModel):


class Results(Protocol):

df: pd.DataFrame

def __getitem__(self, item: str) -> Sequence[float]:
...
def __getitem__(self, item: str) -> Sequence[float]: ...


@dataclasses.dataclass
Expand Down
1 change: 1 addition & 0 deletions agentlib_mpc/models/__init__.py
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
"""
Package containing models for agentlib_mpc.
"""

from agentlib.utils.plugin_import import ModuleImport

MODEL_TYPES = {
Expand Down
7 changes: 4 additions & 3 deletions agentlib_mpc/models/casadi_ml_model.py
Original file line number Diff line number Diff line change
@@ -1,4 +1,5 @@
"""Holds the classes for CasADi variables and the CasADi model."""

import itertools
import logging
from itertools import chain
Expand Down Expand Up @@ -379,9 +380,9 @@ def register_ml_models(
for output in self.config.outputs + self.config.states:
for serialized_output_names, ml_model in ml_model_sources_dict.items():
if output.name in serialized_output_names:
output_to_ml_model[
output.name
] = CasadiPredictor.from_serialized_model(ml_model)
output_to_ml_model[output.name] = (
CasadiPredictor.from_serialized_model(ml_model)
)
ml_model_dict[output.name] = ml_model
casadi_ml_model_dict: Dict[str, CasadiPredictor] = output_to_ml_model
return ml_model_dict, casadi_ml_model_dict
Expand Down
1 change: 1 addition & 0 deletions agentlib_mpc/models/casadi_model.py
Original file line number Diff line number Diff line change
@@ -1,4 +1,5 @@
"""Holds the classes for CasADi variables and the CasADi model."""

import json
import logging
import abc
Expand Down
6 changes: 3 additions & 3 deletions agentlib_mpc/models/casadi_predictor.py
Original file line number Diff line number Diff line change
Expand Up @@ -40,9 +40,9 @@ class Config:
def __init__(self, serialized_model: SerializedMLModel) -> None:
"""Initialize Predictor class."""
self.serialized_model: SerializedMLModel = serialized_model
self.predictor_model: Union[
Sequential, CustomGPR, LinearRegression
] = serialized_model.deserialize()
self.predictor_model: Union[Sequential, CustomGPR, LinearRegression] = (
serialized_model.deserialize()
)
self.sym_input: ca.MX = self._get_sym_input()
self.prediction_function: ca.Function = self._build_prediction_function()

Expand Down
1 change: 1 addition & 0 deletions agentlib_mpc/modules/__init__.py
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,7 @@

It contains classes for local optimization and global coordination.
"""

import importlib


Expand Down
7 changes: 3 additions & 4 deletions agentlib_mpc/modules/data_source.py
Original file line number Diff line number Diff line change
Expand Up @@ -71,7 +71,6 @@ def check_interpolation_method(cls, interpolation_method):


class DataSource(BaseModule):

config: DataSourceConfig

def __init__(self, config: dict, agent: Agent):
Expand All @@ -81,8 +80,9 @@ def __init__(self, config: dict, agent: Agent):

# Filter columns if specified
if self.config.columns:
columns_to_keep = [col for col in self.config.columns if
col in data.columns]
columns_to_keep = [
col for col in self.config.columns if col in data.columns
]
if not columns_to_keep:
raise ValueError("None of the specified columns exist in the dataframe")
data = data[columns_to_keep]
Expand Down Expand Up @@ -112,7 +112,6 @@ def transform_index(self, data: pd.DataFrame) -> pd.DataFrame:
except ValueError:
raise ValueError("Unable to convert index to numeric format")


data.index = data.index.astype(float) - offset
return data

Expand Down
2 changes: 2 additions & 0 deletions agentlib_mpc/modules/dmpc/admm/admm.py
Original file line number Diff line number Diff line change
@@ -1,4 +1,5 @@
"""Holds functionality for ADMM modules."""

import time
import threading
from typing import List, Dict, Tuple, Iterable, Optional, TypeVar, Union
Expand All @@ -23,6 +24,7 @@
import agentlib_mpc.data_structures.admm_datatypes as adt
from agentlib_mpc.data_structures.mpc_datamodels import Results


# noinspection PyArgumentList
class ModuleStatus(Enum):
not_started = auto()
Expand Down
2 changes: 1 addition & 1 deletion agentlib_mpc/modules/dmpc/admm/admm_coordinated.py
Original file line number Diff line number Diff line change
@@ -1,5 +1,6 @@
"""Module implementing the coordinated ADMM module, which works together
with a coordinator."""

from collections import namedtuple
from typing import Dict, Optional
import pandas as pd
Expand Down Expand Up @@ -38,7 +39,6 @@ def __init__(self, *, config: dict, agent: Agent):
self._result: Optional[pd.DataFrame] = None

def process(self):

# send registration request to coordinator
timeout = self.config.registration_interval

Expand Down
7 changes: 3 additions & 4 deletions agentlib_mpc/modules/dmpc/admm/admm_coordinator.py
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
"""
Defines classes that coordinate an ADMM process.
"""

import os
import time
from ast import literal_eval
Expand Down Expand Up @@ -129,11 +130,9 @@ def default_sampling_time(cls, samp_time, info: FieldValidationInfo):


class ADMMCoordinator(Coordinator):

config: ADMMCoordinatorConfig

def __init__(self, *, config: dict, agent: Agent):

if agent.env.config.rt:
self.process = self._realtime_process
self.registration_callback = self._real_time_registration_callback
Expand Down Expand Up @@ -414,7 +413,8 @@ def _check_convergence(self, iteration) -> bool:
if self.config.use_relative_tolerances:
# scaling factors for relative criterion
primal_scaling = max(
np.linalg.norm(flat_locals), np.linalg.norm(flat_means) # Ax # Bz
np.linalg.norm(flat_locals),
np.linalg.norm(flat_means), # Ax # Bz
)
dual_scaling = np.linalg.norm(flat_multipliers)
# compute tolerances for this iteration
Expand Down Expand Up @@ -494,7 +494,6 @@ def trigger_optimizations(self):

# aggregate and send trajectories per agent
for source, agent in active_agents:

# collect mean and multiplier per coupling variable
mean_trajectories = {}
multipliers = {}
Expand Down
1 change: 0 additions & 1 deletion agentlib_mpc/modules/dmpc/coordinator.py
Original file line number Diff line number Diff line change
Expand Up @@ -25,7 +25,6 @@


class CoordinatorConfig(BaseModuleConfig):

maxIter: int = Field(default=10, description="Maximum number of iterations")
time_out_non_responders: float = Field(
default=1, description="Maximum wait time for subsystems in seconds"
Expand Down
1 change: 0 additions & 1 deletion agentlib_mpc/modules/dmpc/employee.py
Original file line number Diff line number Diff line change
Expand Up @@ -43,7 +43,6 @@ class MiniEmployeeConfig(BaseModuleConfig):


class MiniEmployee(BaseModule):

config: MiniEmployeeConfig

def __init__(self, *, config: dict, agent: Agent):
Expand Down
2 changes: 0 additions & 2 deletions agentlib_mpc/modules/ml_model_simulator.py
Original file line number Diff line number Diff line change
Expand Up @@ -10,7 +10,6 @@


class MLModelSimulatorConfig(SimulatorConfig):

serialized_ml_models: AgentVariables = []

@field_validator("t_sample")
Expand All @@ -27,7 +26,6 @@ def check_t_sample(cls, t_sample, info: FieldValidationInfo):


class MLModelSimulator(Simulator):

config: MLModelSimulatorConfig
model: CasadiMLModel

Expand Down
2 changes: 0 additions & 2 deletions agentlib_mpc/modules/ml_model_training/data_reduction.py
Original file line number Diff line number Diff line change
Expand Up @@ -53,7 +53,6 @@ def reduce(


if __name__ == "__main__":

from sklearn.gaussian_process import GaussianProcessRegressor
import matplotlib.pyplot as plt

Expand All @@ -65,7 +64,6 @@ def f(x):
return x[:, 0] * 2 + x[:, 1] * x[:, 0] + x[:, 1] * 3 + 1 / x[:, 1] * x[:, 1]

def get_score(x, y, x_test, y_test, message):

gpr = GaussianProcessRegressor(RBF(), normalize_y=True)
gpr.fit(x, y)
s = gpr.score(x_test, y_test)
Expand Down
6 changes: 3 additions & 3 deletions agentlib_mpc/modules/ml_model_training/setpoint_generator.py
Original file line number Diff line number Diff line change
@@ -1,5 +1,6 @@
"""Module which generates random set points within a comfort zone. Code heavily stolen
from Max Berktold"""
from Max Berktold"""

import datetime
import random

Expand Down Expand Up @@ -38,8 +39,7 @@ def __init__(self, config: dict, agent: Agent):
lb, ub = self._bounds()
self.current_target = random.uniform(lb, ub)

def register_callbacks(self):
...
def register_callbacks(self): ...

def process(self):
while True:
Expand Down
7 changes: 4 additions & 3 deletions agentlib_mpc/modules/mpc.py
EserSteffen marked this conversation as resolved.
Show resolved Hide resolved
Original file line number Diff line number Diff line change
Expand Up @@ -90,6 +90,7 @@ def default_sampling_time(cls, samp_time, info: FieldValidationInfo):
samp_time = info.data["time_step"]
return samp_time


def _create_optimization_backend(optimization_backend, agent_id):
"""Set up the optimization_backend"""
optimization_backend = optimization_backend.copy()
Expand Down Expand Up @@ -278,9 +279,9 @@ def _init_optimization(self):

def re_init_optimization(self, parameter: AgentVariable):
"""Re-initializes the optimization backend with new parameters."""
self.optimization_backend.discretization_options[
parameter.name
] = parameter.value
self.optimization_backend.discretization_options[parameter.name] = (
parameter.value
)
self._init_optimization()

@property
Expand Down
1 change: 1 addition & 0 deletions agentlib_mpc/modules/mpc_full.py
Original file line number Diff line number Diff line change
@@ -1,4 +1,5 @@
"""Holds the class for full featured MPCs."""

import numpy as np
import pandas as pd
from agentlib.core import AgentVariable
Expand Down
7 changes: 4 additions & 3 deletions agentlib_mpc/optimization_backends/casadi_/admm.py
Original file line number Diff line number Diff line change
Expand Up @@ -29,7 +29,6 @@ class CasadiADMMSystem(FullSystem):
penalty_factor: OptimizationParameter

def initialize(self, model: CasadiModel, var_ref: admm_datatypes.VariableReference):

super().initialize(model=model, var_ref=var_ref)

coup_names = [c.name for c in var_ref.couplings]
Expand Down Expand Up @@ -265,7 +264,7 @@ def _discretize(self, sys: CasadiADMMSystem):
self.pred_time = ts * self.k
xk = self.add_opt_var(sys.states)
vars_dict[sys.states.name][self.k] = xk
self.add_constraint(xk-xk_end, gap_closing=True)
self.add_constraint(xk - xk_end, gap_closing=True)

# add model constraints last due to fatrop
self.add_constraint(
Expand Down Expand Up @@ -294,7 +293,9 @@ def _create_ode(
integrator_ode = {"x": x, "p": p, "ode": ode}
if integrator == Integrators.euler:
xk_end = x + ode * opts["tf"]
opt_integrator = ca.Function("system", [x, p], [xk_end], ["x0", "p"], ["xf"])
opt_integrator = ca.Function(
"system", [x, p], [xk_end], ["x0", "p"], ["xf"]
)
else: # rk, cvodes
opt_integrator = ca.integrator("system", integrator, integrator_ode, opts)
return opt_integrator
Expand Down
18 changes: 10 additions & 8 deletions agentlib_mpc/optimization_backends/casadi_/basic.py
Original file line number Diff line number Diff line change
Expand Up @@ -43,7 +43,6 @@ class BaseSystem(System):
ode: ca.MX

def initialize(self, model: CasadiModel, var_ref: VariableReference):

# define variables
self.states = OptimizationVariable.declare(
denotation="state",
Expand Down Expand Up @@ -171,7 +170,6 @@ def _discretize(self, sys: BaseSystem):
for constraint in constraints:
self.add_constraint(*constraint)


def _construct_stage_function(self, system: BaseSystem):
"""
Combine information from the model and the var_ref to create CasADi
Expand Down Expand Up @@ -322,11 +320,13 @@ def _collocation_inner_loop(
)

constraints.append((ts * stage["ode"] - xp,))
constraints.append((
stage["model_constraints"],
stage["lb_model_constraints"],
stage["ub_model_constraints"],
))
constraints.append(
(
stage["model_constraints"],
stage["lb_model_constraints"],
stage["ub_model_constraints"],
)
)

# Add contribution to the end state
state_k_end = state_k_end + collocation.D[j] * state_collocation[j - 1]
Expand Down Expand Up @@ -458,7 +458,9 @@ def _create_ode(self, sys: BaseSystem, opts: dict, integrator: Integrators):

if integrator == Integrators.euler:
xk_end = x + ode * opts["tf"]
opt_integrator = ca.Function("system", [x, p], [xk_end], ["x0", "p"], ["xf"])
opt_integrator = ca.Function(
"system", [x, p], [xk_end], ["x0", "p"], ["xf"]
)
else: # rk, cvodes
opt_integrator = ca.integrator("system", integrator, integrator_ode, opts)

Expand Down
11 changes: 9 additions & 2 deletions agentlib_mpc/optimization_backends/casadi_/casadi_ml.py
Original file line number Diff line number Diff line change
Expand Up @@ -73,14 +73,16 @@ def initialize(self, model: CasadiMLModel, var_ref: FullVariableReference):
ref_list=var_ref.parameters,
)
self.initial_state = OptimizationParameter.declare(
denotation="initial_state", # append the 0 as a convention to get initial guess
denotation="initial_state",
# append the 0 as a convention to get initial guess
variables=model.get_states(var_ref.states),
ref_list=var_ref.states,
use_in_stage_function=False,
assert_complete=True,
)
EserSteffen marked this conversation as resolved.
Show resolved Hide resolved
self.last_control = OptimizationParameter.declare(
denotation="initial_control", # append the 0 as a convention to get initial guess
denotation="initial_control",
# append the 0 as a convention to get initial guess
variables=model.get_inputs(var_ref.controls),
ref_list=var_ref.controls,
use_in_stage_function=False,
Expand Down Expand Up @@ -147,6 +149,11 @@ def _discretize(self, sys: CasadiMLSystem):
sys.states, lb=x_past, ub=x_past, guess=x_past
)
mx_dict[time][sys.initial_state.name] = x_past
z_past = self.add_opt_par(sys.algebraics)
mx_dict[time][sys.algebraics.name] = self.add_opt_var(
sys.algebraics, lb=z_past, ub=z_past, guess=z_past
)
mx_dict[time][sys.algebraics.name] = z_past
EserSteffen marked this conversation as resolved.
Show resolved Hide resolved

# add past inputs
for time in pre_grid_inputs:
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -118,7 +118,7 @@ def setup_optimization(self, var_ref: mpc_datamodels.VariableReference):
bat_file=self.config.build_batch_bat,
name=self.config.name,
options=self.config.solver,
logger=self.logger
logger=self.logger,
)
self.discretization.initialize(
system=self.system, solver_factory=solver_factory
Expand Down
Loading