From 0d262c41893ac9fb5515bbba367a5e69afa5e1fd Mon Sep 17 00:00:00 2001 From: Robin Steuteville Date: Tue, 11 Jun 2024 15:38:52 -0600 Subject: [PATCH 01/15] /Users/rsteutev/Documents/GitHub/fastsim/fastsim-venv/bin/python --- python/fastsim/demos/demo_conv.py | 2 ++ 1 file changed, 2 insertions(+) diff --git a/python/fastsim/demos/demo_conv.py b/python/fastsim/demos/demo_conv.py index ed086662..8c94d65d 100644 --- a/python/fastsim/demos/demo_conv.py +++ b/python/fastsim/demos/demo_conv.py @@ -30,6 +30,8 @@ # load cycle from file cyc = fsim.Cycle.from_resource("cycles/udds.csv") +print(veh.param_path_list()) + # instantiate `SimDrive` simulation object sd = fsim.SimDrive(veh, cyc) From b40c9038f9a518091663543a03321ebe6c692019 Mon Sep 17 00:00:00 2001 From: Robin Steuteville Date: Tue, 11 Jun 2024 17:31:38 -0600 Subject: [PATCH 02/15] creating function that returns variable paths of a struct --- python/fastsim/__init__.py | 86 ++++++++++++++++++++++++++++++++++++++ 1 file changed, 86 insertions(+) diff --git a/python/fastsim/__init__.py b/python/fastsim/__init__.py index 956650b3..4575384d 100644 --- a/python/fastsim/__init__.py +++ b/python/fastsim/__init__.py @@ -2,6 +2,7 @@ from typing import Union, Any import numpy as np import re +import inspect from .fastsim import * @@ -71,4 +72,89 @@ def _get_list(path_elem, container): def __array__(self): return np.array(self.tolist()) +# def get_class_variables(cls: type) -> set[str]: +# """Return set of class variables.""" +# # Get class attributes +# attributes = vars(cls) + +# # Filter out methods, nested classes and dunder (__) attributes +# return { +# key for key, value in attributes.items() +# if not callable(value) and not key.startswith("__") +# } + +# https://www.geeksforgeeks.org/get-variable-name-as-string-in-python/ +# https://www.geeksforgeeks.org/how-to-print-a-variables-name-in-python/ +def print_variable(variable): + variable_name = [name for name, value in globals().items() if value is variable][0] + print(f"Variable name using globals(): {variable_name}") + return variable_name + +ACCEPTED_RUST_STRUCTS = ['FuelConverter', + 'FuelConverterState', + 'FuelConverterStateHistoryVec', + 'ReversibleEnergyStorage', + 'ReversibleEnergyStorageState', + 'ReversibleEnergyStorageStateHistoryVec', + 'ElectricMachine', + 'ElectricMachineState', + 'ElectricMachineStateHistoryVec', + 'Cycle', + 'CycleElement', + 'Vehicle', + 'SimDrive', + 'SimParams', + 'RustSimDrive', + 'Pyo3VecWrapper', + 'Pyo3Vec2Wrapper', + 'Pyo3Vec3Wrapper', + 'Pyo3VecBoolWrapper'] + +def param_path_list(self, path = "", param_path_list = []) -> list[str]: + if path == "": + # path = str(print_variable(self)) + path = type(self).__name__ + # else: + # path = path + "." + name + variable_list = [attr for attr in self.__dir__() if not attr.startswith("__") and not callable(getattr(self,attr))] + print(variable_list) + for variable in variable_list: + if not type(getattr(self,variable)).__name__ in ACCEPTED_RUST_STRUCTS: + variable_path = path + "." + variable + print("variable type not in list: ", variable_path, type(getattr(self,variable)).__name__) + param_path_list.append(variable_path) + elif len([attr for attr in getattr(self,variable).__dir__() if not attr.startswith("__") and not callable(getattr(getattr(self,variable),attr))]) == 0: + variable_path = path + "." + variable + print("variable length zero: ", variable_path, type(getattr(self,variable)).__name__) + param_path_list.append(variable_path) + else: + variable_path = path + "." + variable + print("variable treated as struct: ", variable_path, type(getattr(self,variable)).__name__) + param_path_list = getattr(self,variable).param_path_list(path = variable_path, param_path_list = param_path_list) + return param_path_list + + + + setattr(Pyo3VecWrapper, "__array__", __array__) # noqa: F405 +# add param_path_list as an attribute for all Rust structs +setattr(FuelConverter, "param_path_list", param_path_list) +setattr(FuelConverterState, "param_path_list", param_path_list) +setattr(FuelConverterStateHistoryVec, "param_path_list", param_path_list) +setattr(ReversibleEnergyStorage, "param_path_list", param_path_list) +setattr(ReversibleEnergyStorageState, "param_path_list", param_path_list) +setattr(ReversibleEnergyStorageStateHistoryVec, "param_path_list", param_path_list) +setattr(ElectricMachine, "param_path_list", param_path_list) +setattr(ElectricMachineState, "param_path_list", param_path_list) +setattr(ElectricMachineStateHistoryVec, "param_path_list", param_path_list) +setattr(Cycle, "param_path_list", param_path_list) +setattr(CycleElement, "param_path_list", param_path_list) +setattr(Vehicle, "param_path_list", param_path_list) +# setattr(VehicleStateHistoryVec, "param_path_list", param_path_list) +setattr(SimDrive, "param_path_list", param_path_list) +# setattr(SimParams, "param_path_list", param_path_list) +setattr(RustSimDrive, "param_path_list", param_path_list) +setattr(Pyo3VecWrapper, "param_path_list", param_path_list) +setattr(Pyo3Vec2Wrapper, "param_path_list", param_path_list) +setattr(Pyo3Vec3Wrapper, "param_path_list", param_path_list) +setattr(Pyo3VecBoolWrapper, "param_path_list", param_path_list) \ No newline at end of file From 8bdaeb9da02f21e13a91594289853fedfbc9f5a3 Mon Sep 17 00:00:00 2001 From: Robin Steuteville Date: Wed, 12 Jun 2024 14:03:45 -0600 Subject: [PATCH 03/15] demo testing --- python/fastsim/demos/demo_conv.py | 6 +++++- 1 file changed, 5 insertions(+), 1 deletion(-) diff --git a/python/fastsim/demos/demo_conv.py b/python/fastsim/demos/demo_conv.py index 8c94d65d..10729730 100644 --- a/python/fastsim/demos/demo_conv.py +++ b/python/fastsim/demos/demo_conv.py @@ -12,7 +12,8 @@ sns.set_theme() -SHOW_PLOTS = os.environ.get("SHOW_PLOTS", "true").lower() == "true" +SHOW_PLOTS = os.environ.get("SHOW_PLOTS", "true").lower() == "true" +SHOW_PLOTS = False # %% [markdown] @@ -35,6 +36,9 @@ # instantiate `SimDrive` simulation object sd = fsim.SimDrive(veh, cyc) +# print([attr for attr in sd.__dir__() if not attr.startswith("__") and not callable(getattr(sd,attr))]) +# print(sd.param_path_list()) + # simulation start time t0 = time.perf_counter() # run simulation From cfd82b2dd4b0acd4d1cf3553bd61cde60bead499 Mon Sep 17 00:00:00 2001 From: Robin Steuteville Date: Thu, 13 Jun 2024 17:29:49 -0600 Subject: [PATCH 04/15] adding history_path_list function and adding doc strings --- python/fastsim/__init__.py | 87 +++++++++++++++++++------------ python/fastsim/demos/demo_conv.py | 2 + 2 files changed, 57 insertions(+), 32 deletions(-) diff --git a/python/fastsim/__init__.py b/python/fastsim/__init__.py index 4575384d..0c47873f 100644 --- a/python/fastsim/__init__.py +++ b/python/fastsim/__init__.py @@ -72,24 +72,9 @@ def _get_list(path_elem, container): def __array__(self): return np.array(self.tolist()) -# def get_class_variables(cls: type) -> set[str]: -# """Return set of class variables.""" -# # Get class attributes -# attributes = vars(cls) - -# # Filter out methods, nested classes and dunder (__) attributes -# return { -# key for key, value in attributes.items() -# if not callable(value) and not key.startswith("__") -# } - -# https://www.geeksforgeeks.org/get-variable-name-as-string-in-python/ -# https://www.geeksforgeeks.org/how-to-print-a-variables-name-in-python/ -def print_variable(variable): - variable_name = [name for name, value in globals().items() if value is variable][0] - print(f"Variable name using globals(): {variable_name}") - return variable_name - + +# for param_path_list() method to identify something as a struct so that it +# checks for sub-variables and sub-structs, it must be added to this list: ACCEPTED_RUST_STRUCTS = ['FuelConverter', 'FuelConverterState', 'FuelConverterStateHistoryVec', @@ -111,32 +96,52 @@ def print_variable(variable): 'Pyo3VecBoolWrapper'] def param_path_list(self, path = "", param_path_list = []) -> list[str]: - if path == "": - # path = str(print_variable(self)) - path = type(self).__name__ - # else: - # path = path + "." + name + """Returns list of relative paths to all variables and sub-variables within + class (relative to the class the method was called on) + Arguments: + ---------- + path : Defaults to empty string. This is mainly used within the method in + order to call the method recursively and does not need to be specified by + user. Specifies a path to be added in front of all paths returned by the + method. + param_path_list : Defaults to empty list. This is mainly used within the + method in order to call the method recursively and does not need to be + specified by user. Specifies a list of paths to be appended to the list + returned by the method. + """ variable_list = [attr for attr in self.__dir__() if not attr.startswith("__") and not callable(getattr(self,attr))] print(variable_list) for variable in variable_list: if not type(getattr(self,variable)).__name__ in ACCEPTED_RUST_STRUCTS: - variable_path = path + "." + variable - print("variable type not in list: ", variable_path, type(getattr(self,variable)).__name__) + if path == "": + variable_path = variable + else: + variable_path = path + "." + variable param_path_list.append(variable_path) elif len([attr for attr in getattr(self,variable).__dir__() if not attr.startswith("__") and not callable(getattr(getattr(self,variable),attr))]) == 0: - variable_path = path + "." + variable - print("variable length zero: ", variable_path, type(getattr(self,variable)).__name__) + if path == "": + variable_path = variable + else: + variable_path = path + "." + variable param_path_list.append(variable_path) else: - variable_path = path + "." + variable - print("variable treated as struct: ", variable_path, type(getattr(self,variable)).__name__) + if path == "": + variable_path = variable + else: + variable_path = path + "." + variable param_path_list = getattr(self,variable).param_path_list(path = variable_path, param_path_list = param_path_list) return param_path_list + +def history_path_list(self) -> list[str]: + """Returns a list of relative paths to all history variables (all variables + that contain history as a subpath).""" + return [item for item in self.param_path_list() if "history" in item] setattr(Pyo3VecWrapper, "__array__", __array__) # noqa: F405 + # add param_path_list as an attribute for all Rust structs setattr(FuelConverter, "param_path_list", param_path_list) setattr(FuelConverterState, "param_path_list", param_path_list) @@ -150,11 +155,29 @@ def param_path_list(self, path = "", param_path_list = []) -> list[str]: setattr(Cycle, "param_path_list", param_path_list) setattr(CycleElement, "param_path_list", param_path_list) setattr(Vehicle, "param_path_list", param_path_list) -# setattr(VehicleStateHistoryVec, "param_path_list", param_path_list) setattr(SimDrive, "param_path_list", param_path_list) -# setattr(SimParams, "param_path_list", param_path_list) setattr(RustSimDrive, "param_path_list", param_path_list) setattr(Pyo3VecWrapper, "param_path_list", param_path_list) setattr(Pyo3Vec2Wrapper, "param_path_list", param_path_list) setattr(Pyo3Vec3Wrapper, "param_path_list", param_path_list) -setattr(Pyo3VecBoolWrapper, "param_path_list", param_path_list) \ No newline at end of file +setattr(Pyo3VecBoolWrapper, "param_path_list", param_path_list) + +# add history_path_list as an attribute for all Rust structs +setattr(FuelConverter, "history_path_list", history_path_list) +setattr(FuelConverterState, "history_path_list", history_path_list) +setattr(FuelConverterStateHistoryVec, "history_path_list", history_path_list) +setattr(ReversibleEnergyStorage, "history_path_list", history_path_list) +setattr(ReversibleEnergyStorageState, "history_path_list", history_path_list) +setattr(ReversibleEnergyStorageStateHistoryVec, "history_path_list", history_path_list) +setattr(ElectricMachine, "history_path_list", history_path_list) +setattr(ElectricMachineState, "history_path_list", history_path_list) +setattr(ElectricMachineStateHistoryVec, "history_path_list", history_path_list) +setattr(Cycle, "history_path_list", history_path_list) +setattr(CycleElement, "history_path_list", history_path_list) +setattr(Vehicle, "history_path_list", history_path_list) +setattr(SimDrive, "history_path_list", history_path_list) +setattr(RustSimDrive, "history_path_list", history_path_list) +setattr(Pyo3VecWrapper, "history_path_list", history_path_list) +setattr(Pyo3Vec2Wrapper, "history_path_list", history_path_list) +setattr(Pyo3Vec3Wrapper, "history_path_list", history_path_list) +setattr(Pyo3VecBoolWrapper, "history_path_list", history_path_list) \ No newline at end of file diff --git a/python/fastsim/demos/demo_conv.py b/python/fastsim/demos/demo_conv.py index 10729730..41414b33 100644 --- a/python/fastsim/demos/demo_conv.py +++ b/python/fastsim/demos/demo_conv.py @@ -33,6 +33,8 @@ print(veh.param_path_list()) +print(veh.history_path_list()) + # instantiate `SimDrive` simulation object sd = fsim.SimDrive(veh, cyc) From d27002fb81c804ea99adc3755caa996c1b785d46 Mon Sep 17 00:00:00 2001 From: Robin Steuteville Date: Fri, 14 Jun 2024 16:27:12 -0600 Subject: [PATCH 05/15] fixing problem with Cycle.grade and adding demo file for param paths --- fastsim-core/src/drive_cycle.rs | 9 ++++-- python/fastsim/__init__.py | 8 ++--- python/fastsim/demos/demo_conv.py | 7 ----- python/fastsim/demos/demo_param_paths.py | 37 ++++++++++++++++++++++++ 4 files changed, 48 insertions(+), 13 deletions(-) create mode 100644 python/fastsim/demos/demo_param_paths.py diff --git a/fastsim-core/src/drive_cycle.rs b/fastsim-core/src/drive_cycle.rs index 81b23ff0..72bc7b06 100644 --- a/fastsim-core/src/drive_cycle.rs +++ b/fastsim-core/src/drive_cycle.rs @@ -6,10 +6,15 @@ use fastsim_2::cycle::RustCycle as Cycle2; self.len() } - #[setter] - fn set_grade(&mut self, grade: Vec) { + #[setter("__grade")] + fn set_grade_py(&mut self, grade: Vec) { self.grade = grade.iter().map(|x| *x * uc::R).collect(); } + + #[getter] + fn get_grade_py(&self) -> Vec { + self.grade.iter().map(|x| x.get::()).collect() + } )] #[derive(Clone, Debug, Deserialize, Serialize, PartialEq, Default)] /// Container diff --git a/python/fastsim/__init__.py b/python/fastsim/__init__.py index 0c47873f..64b434ab 100644 --- a/python/fastsim/__init__.py +++ b/python/fastsim/__init__.py @@ -88,7 +88,6 @@ def __array__(self): 'CycleElement', 'Vehicle', 'SimDrive', - 'SimParams', 'RustSimDrive', 'Pyo3VecWrapper', 'Pyo3Vec2Wrapper', @@ -97,7 +96,8 @@ def __array__(self): def param_path_list(self, path = "", param_path_list = []) -> list[str]: """Returns list of relative paths to all variables and sub-variables within - class (relative to the class the method was called on) + class (relative to the class the method was called on) + See example usage in demo_param_paths.py. Arguments: ---------- path : Defaults to empty string. This is mainly used within the method in @@ -110,7 +110,6 @@ class (relative to the class the method was called on) returned by the method. """ variable_list = [attr for attr in self.__dir__() if not attr.startswith("__") and not callable(getattr(self,attr))] - print(variable_list) for variable in variable_list: if not type(getattr(self,variable)).__name__ in ACCEPTED_RUST_STRUCTS: if path == "": @@ -134,7 +133,8 @@ class (relative to the class the method was called on) def history_path_list(self) -> list[str]: """Returns a list of relative paths to all history variables (all variables - that contain history as a subpath).""" + that contain history as a subpath). + See example usage in demo_param_paths.py.""" return [item for item in self.param_path_list() if "history" in item] diff --git a/python/fastsim/demos/demo_conv.py b/python/fastsim/demos/demo_conv.py index 41414b33..a03e3e10 100644 --- a/python/fastsim/demos/demo_conv.py +++ b/python/fastsim/demos/demo_conv.py @@ -31,16 +31,9 @@ # load cycle from file cyc = fsim.Cycle.from_resource("cycles/udds.csv") -print(veh.param_path_list()) - -print(veh.history_path_list()) - # instantiate `SimDrive` simulation object sd = fsim.SimDrive(veh, cyc) -# print([attr for attr in sd.__dir__() if not attr.startswith("__") and not callable(getattr(sd,attr))]) -# print(sd.param_path_list()) - # simulation start time t0 = time.perf_counter() # run simulation diff --git a/python/fastsim/demos/demo_param_paths.py b/python/fastsim/demos/demo_param_paths.py new file mode 100644 index 00000000..aaed0dd8 --- /dev/null +++ b/python/fastsim/demos/demo_param_paths.py @@ -0,0 +1,37 @@ +# %% + +import numpy as np +import matplotlib.pyplot as plt +from matplotlib import rc_params +from cycler import cycler +import seaborn as sns +import time +import json +import os +import fastsim as fsim + +# %% [markdown] + +# `fastsim3` -- load vehicle, cycle and simdrive, and demonstrate usage of methods +# `param_path_list()` and `history_path_list()` +# %% + +# load 2012 Ford Fusion from file +veh = fsim.Vehicle.from_file( + str(fsim.package_root() / "../../tests/assets/2012_Ford_Fusion.yaml") +) + +# Set `save_interval` at vehicle level -- cascades to all sub-components with time-varying states +veh.save_interval = 1 + +# load cycle from file +cyc = fsim.Cycle.from_resource("cycles/udds.csv") + +# instantiate `SimDrive` simulation object +sd = fsim.SimDrive(veh, cyc) + +# print out all subpaths for variables in SimDrive +print("List of variable paths for SimDrive: ", sd.param_path_list()) + +# print out all subpaths for history variables in SimDrive +print("List of history variable paths for SimDrive: ", sd.history_path_list()) \ No newline at end of file From f45a21f9ed49192cee9529e30063af11984e03fc Mon Sep 17 00:00:00 2001 From: Robin Steuteville Date: Sun, 16 Jun 2024 16:35:52 -0600 Subject: [PATCH 06/15] adding unit test for param_path_list() and history_path_list() --- python/fastsim/tests/test_param_paths.py | 28 ++++++++++++++++++++++++ 1 file changed, 28 insertions(+) create mode 100644 python/fastsim/tests/test_param_paths.py diff --git a/python/fastsim/tests/test_param_paths.py b/python/fastsim/tests/test_param_paths.py new file mode 100644 index 00000000..565e99cd --- /dev/null +++ b/python/fastsim/tests/test_param_paths.py @@ -0,0 +1,28 @@ +import unittest +import fastsim as fsim + +class TestParamPath(unittest.TestCase): + def test_param_path_list(self): + # load 2012 Ford Fusion from file + veh = fsim.Vehicle.from_file( + str(fsim.package_root() / "../../tests/assets/2012_Ford_Fusion.yaml") + ) + baseline_variable_paths = ['fc.eff_min', 'fc.pwr_out_frac_interp', 'fc.pwr_ramp_lag_seconds', 'fc.pwr_ramp_lag_hours', 'fc.pwr_idle_fuel_watts', 'fc.mass_kg', 'fc.eff_range', + 'fc.state.pwr_loss_watts', 'fc.state.pwr_tractive_watts', 'fc.state.pwr_aux_watts', 'fc.state.pwr_fuel_watts', 'fc.state.energy_fuel_joules', + 'fc.state.energy_tractive_joules', 'fc.state.eff', 'fc.state.energy_loss_joules', 'fc.state.energy_aux_joules', 'fc.state.fc_on', + 'fc.state.pwr_prop_max_watts', 'fc.state.i', 'fc.eff_max', 'fc.specific_pwr_kw_per_kg', 'fc.pwr_out_max_watts', 'fc.history.i', + 'fc.history.pwr_prop_max_watts', 'fc.history.pwr_tractive_watts', 'fc.history.energy_aux_joules', 'fc.history.pwr_fuel_watts', + 'fc.history.energy_loss_joules', 'fc.history.fc_on', 'fc.history.pwr_aux_watts', 'fc.history.energy_tractive_joules', 'fc.history.energy_fuel_joules', + 'fc.history.pwr_loss_watts', 'fc.history.eff', 'fc.pwr_out_max_init_watts', 'fc.eff_interp', 'fc.save_interval', 'pwr_aux_watts', 'trans_eff', 'state', + 'chassis', 'year', 'save_interval', 'history', 'name'] + baseline_history_variable_paths = ['fc.history.i', 'fc.history.pwr_prop_max_watts', 'fc.history.pwr_tractive_watts', 'fc.history.energy_aux_joules', 'fc.history.pwr_fuel_watts', + 'fc.history.energy_loss_joules', 'fc.history.fc_on', 'fc.history.pwr_aux_watts', 'fc.history.energy_tractive_joules', 'fc.history.energy_fuel_joules', + 'fc.history.pwr_loss_watts', 'fc.history.eff', 'history', 'fc.history.i', 'fc.history.pwr_prop_max_watts', 'fc.history.pwr_tractive_watts', + 'fc.history.energy_aux_joules', 'fc.history.pwr_fuel_watts', 'fc.history.energy_loss_joules', 'fc.history.fc_on', 'fc.history.pwr_aux_watts', + 'fc.history.energy_tractive_joules', 'fc.history.energy_fuel_joules', 'fc.history.pwr_loss_watts', 'fc.history.eff', 'history'] + assert(baseline_variable_paths.sort()==veh.param_path_list().sort()) + assert(baseline_history_variable_paths.sort()==veh.history_path_list().sort()) + + +if __name__ == '__main__': + unittest.main() \ No newline at end of file From faf8fa6057012c40e61fa8e327dedf8f43a7e47b Mon Sep 17 00:00:00 2001 From: Robin Steuteville Date: Sun, 16 Jun 2024 17:01:48 -0600 Subject: [PATCH 07/15] updating readme formatting --- README.md | 1 + 1 file changed, 1 insertion(+) diff --git a/README.md b/README.md index f920c25e..0523a68c 100644 --- a/README.md +++ b/README.md @@ -81,3 +81,4 @@ Matthew Moniot -- Matthew.Moniot@nrel.gov Grant Payne -- Grant.Payne@nrel.gov Laurie Ramroth -- lramroth@ford.com Eric Wood -- Eric.Wood@nrel.gov +Robin Steuteville -- Robin.Steuteville@nrel.gov From 9a00380e0ba947c7ea889b6bbfb3fda57d3e2c92 Mon Sep 17 00:00:00 2001 From: Robin Steuteville Date: Sun, 16 Jun 2024 17:06:15 -0600 Subject: [PATCH 08/15] cleaning up code --- python/fastsim/__init__.py | 1 - python/fastsim/demos/demo_conv.py | 1 - 2 files changed, 2 deletions(-) diff --git a/python/fastsim/__init__.py b/python/fastsim/__init__.py index d0060234..e87d77c0 100644 --- a/python/fastsim/__init__.py +++ b/python/fastsim/__init__.py @@ -2,7 +2,6 @@ from typing import Union, Any import numpy as np import re -import inspect from .fastsim import * diff --git a/python/fastsim/demos/demo_conv.py b/python/fastsim/demos/demo_conv.py index a03e3e10..64816b95 100644 --- a/python/fastsim/demos/demo_conv.py +++ b/python/fastsim/demos/demo_conv.py @@ -13,7 +13,6 @@ sns.set_theme() SHOW_PLOTS = os.environ.get("SHOW_PLOTS", "true").lower() == "true" -SHOW_PLOTS = False # %% [markdown] From 165244b3b7348aa12e58889e187804ba5c6343fb Mon Sep 17 00:00:00 2001 From: Robin Steuteville Date: Sun, 16 Jun 2024 17:27:48 -0600 Subject: [PATCH 09/15] fixing type error --- python/fastsim/__init__.py | 6 +++--- python/fastsim/demos/demo_param_paths.py | 9 --------- 2 files changed, 3 insertions(+), 12 deletions(-) diff --git a/python/fastsim/__init__.py b/python/fastsim/__init__.py index e87d77c0..786bd341 100644 --- a/python/fastsim/__init__.py +++ b/python/fastsim/__init__.py @@ -1,5 +1,5 @@ from pathlib import Path -from typing import Union, Any +from typing import Any, List import numpy as np import re @@ -95,7 +95,7 @@ def __array__(self): 'Pyo3Vec3Wrapper', 'Pyo3VecBoolWrapper'] -def param_path_list(self, path = "", param_path_list = []) -> list[str]: +def param_path_list(self, path = "", param_path_list = []) -> List[str]: """Returns list of relative paths to all variables and sub-variables within class (relative to the class the method was called on) See example usage in demo_param_paths.py. @@ -132,7 +132,7 @@ class (relative to the class the method was called on) param_path_list = getattr(self,variable).param_path_list(path = variable_path, param_path_list = param_path_list) return param_path_list -def history_path_list(self) -> list[str]: +def history_path_list(self) -> List[str]: """Returns a list of relative paths to all history variables (all variables that contain history as a subpath). See example usage in demo_param_paths.py.""" diff --git a/python/fastsim/demos/demo_param_paths.py b/python/fastsim/demos/demo_param_paths.py index aaed0dd8..0fd52f37 100644 --- a/python/fastsim/demos/demo_param_paths.py +++ b/python/fastsim/demos/demo_param_paths.py @@ -1,13 +1,4 @@ # %% - -import numpy as np -import matplotlib.pyplot as plt -from matplotlib import rc_params -from cycler import cycler -import seaborn as sns -import time -import json -import os import fastsim as fsim # %% [markdown] From 3831a180217ac6d8dd9b53c8916806b30c7e364e Mon Sep 17 00:00:00 2001 From: Robin Steuteville Date: Sun, 23 Jun 2024 18:26:42 -0400 Subject: [PATCH 10/15] updating based on Chad's comments --- python/fastsim/__init__.py | 115 ++++++------------ ..._param_paths.py => demo_variable_paths.py} | 14 +-- ..._param_paths.py => test_variable_paths.py} | 2 +- 3 files changed, 43 insertions(+), 88 deletions(-) rename python/fastsim/demos/{demo_param_paths.py => demo_variable_paths.py} (73%) rename python/fastsim/tests/{test_param_paths.py => test_variable_paths.py} (97%) diff --git a/python/fastsim/__init__.py b/python/fastsim/__init__.py index 786bd341..151a298d 100644 --- a/python/fastsim/__init__.py +++ b/python/fastsim/__init__.py @@ -2,8 +2,10 @@ from typing import Any, List import numpy as np import re +import inspect from .fastsim import * +import fastsim as fsim def package_root() -> Path: """Returns the package root directory.""" @@ -74,41 +76,26 @@ def __array__(self): return np.array(self.tolist()) -# for param_path_list() method to identify something as a struct so that it -# checks for sub-variables and sub-structs, it must be added to this list: -ACCEPTED_RUST_STRUCTS = ['FuelConverter', - 'FuelConverterState', - 'FuelConverterStateHistoryVec', - 'ReversibleEnergyStorage', - 'ReversibleEnergyStorageState', - 'ReversibleEnergyStorageStateHistoryVec', - 'ElectricMachine', - 'ElectricMachineState', - 'ElectricMachineStateHistoryVec', - 'Cycle', - 'CycleElement', - 'Vehicle', - 'SimDrive', - 'RustSimDrive', - 'Pyo3VecWrapper', - 'Pyo3Vec2Wrapper', - 'Pyo3Vec3Wrapper', - 'Pyo3VecBoolWrapper'] - -def param_path_list(self, path = "", param_path_list = []) -> List[str]: +# creates a list of all python classes from rust structs that need variable_path_list() and +# history_path_list() added as methods +ACCEPTED_RUST_STRUCTS = [attr for attr in fsim.__dir__() if not\ + attr.startswith("__") and\ + isinstance(getattr(fsim,attr), type) and\ + attr[0].isupper() and\ + ("fastsim" in str(inspect.getmodule(getattr(fsim,attr))))] + +def variable_path_list(self, path = "", variable_path_list = []) -> List[str]: """Returns list of relative paths to all variables and sub-variables within - class (relative to the class the method was called on) - See example usage in demo_param_paths.py. - Arguments: - ---------- - path : Defaults to empty string. This is mainly used within the method in - order to call the method recursively and does not need to be specified by - user. Specifies a path to be added in front of all paths returned by the - method. - param_path_list : Defaults to empty list. This is mainly used within the - method in order to call the method recursively and does not need to be - specified by user. Specifies a list of paths to be appended to the list - returned by the method. + class (relative to the class the method was called on) See example usage in + demo_param_paths.py. + Arguments: ---------- + path : Defaults to empty string. This is mainly used within the method in + order to call the method recursively and should not be specified by user. + Specifies a path to be added in front of all paths returned by the method. + variable_path_list : Defaults to empty list. This is mainly used within the + method in order to call the method recursively and should not be specified + by user. Specifies a list of paths to be appended to the list returned by + the method. """ variable_list = [attr for attr in self.__dir__() if not attr.startswith("__") and not callable(getattr(self,attr))] for variable in variable_list: @@ -117,68 +104,38 @@ class (relative to the class the method was called on) variable_path = variable else: variable_path = path + "." + variable - param_path_list.append(variable_path) - elif len([attr for attr in getattr(self,variable).__dir__() if not attr.startswith("__") and not callable(getattr(getattr(self,variable),attr))]) == 0: + variable_path_list.append(variable_path) + elif len([attr for attr in getattr(self,variable).__dir__() if not attr.startswith("__")\ + and not callable(getattr(getattr(self,variable),attr))]) == 0: if path == "": variable_path = variable else: variable_path = path + "." + variable - param_path_list.append(variable_path) + variable_path_list.append(variable_path) else: if path == "": variable_path = variable else: variable_path = path + "." + variable - param_path_list = getattr(self,variable).param_path_list(path = variable_path, param_path_list = param_path_list) - return param_path_list + variable_path_list = getattr(self,variable).variable_path_list(path = variable_path,\ + variable_path_list = variable_path_list) + return variable_path_list def history_path_list(self) -> List[str]: """Returns a list of relative paths to all history variables (all variables that contain history as a subpath). See example usage in demo_param_paths.py.""" - return [item for item in self.param_path_list() if "history" in item] + return [item for item in self.variable_path_list() if "history" in item] setattr(Pyo3VecWrapper, "__array__", __array__) # noqa: F405 -# add param_path_list as an attribute for all Rust structs -setattr(FuelConverter, "param_path_list", param_path_list) -setattr(FuelConverterState, "param_path_list", param_path_list) -setattr(FuelConverterStateHistoryVec, "param_path_list", param_path_list) -setattr(ReversibleEnergyStorage, "param_path_list", param_path_list) -setattr(ReversibleEnergyStorageState, "param_path_list", param_path_list) -setattr(ReversibleEnergyStorageStateHistoryVec, "param_path_list", param_path_list) -setattr(ElectricMachine, "param_path_list", param_path_list) -setattr(ElectricMachineState, "param_path_list", param_path_list) -setattr(ElectricMachineStateHistoryVec, "param_path_list", param_path_list) -setattr(Cycle, "param_path_list", param_path_list) -setattr(CycleElement, "param_path_list", param_path_list) -setattr(Vehicle, "param_path_list", param_path_list) -setattr(SimDrive, "param_path_list", param_path_list) -setattr(RustSimDrive, "param_path_list", param_path_list) -setattr(Pyo3VecWrapper, "param_path_list", param_path_list) -setattr(Pyo3Vec2Wrapper, "param_path_list", param_path_list) -setattr(Pyo3Vec3Wrapper, "param_path_list", param_path_list) -setattr(Pyo3VecBoolWrapper, "param_path_list", param_path_list) - -# add history_path_list as an attribute for all Rust structs -setattr(FuelConverter, "history_path_list", history_path_list) -setattr(FuelConverterState, "history_path_list", history_path_list) -setattr(FuelConverterStateHistoryVec, "history_path_list", history_path_list) -setattr(ReversibleEnergyStorage, "history_path_list", history_path_list) -setattr(ReversibleEnergyStorageState, "history_path_list", history_path_list) -setattr(ReversibleEnergyStorageStateHistoryVec, "history_path_list", history_path_list) -setattr(ElectricMachine, "history_path_list", history_path_list) -setattr(ElectricMachineState, "history_path_list", history_path_list) -setattr(ElectricMachineStateHistoryVec, "history_path_list", history_path_list) -setattr(Cycle, "history_path_list", history_path_list) -setattr(CycleElement, "history_path_list", history_path_list) -setattr(Vehicle, "history_path_list", history_path_list) -setattr(SimDrive, "history_path_list", history_path_list) -setattr(RustSimDrive, "history_path_list", history_path_list) -setattr(Pyo3VecWrapper, "history_path_list", history_path_list) -setattr(Pyo3Vec2Wrapper, "history_path_list", history_path_list) -setattr(Pyo3Vec3Wrapper, "history_path_list", history_path_list) -setattr(Pyo3VecBoolWrapper, "history_path_list", history_path_list) \ No newline at end of file +# adds variable_path_list() and history_path_list() as methods to all classes in +# ACCEPTED_RUST_STRUCTS +for item in ACCEPTED_RUST_STRUCTS: + print("starting", item) + setattr(getattr(fsim, item), "variable_path_list", variable_path_list) + setattr(getattr(fsim, item), "history_path_list", history_path_list) + print(item, "finished!") \ No newline at end of file diff --git a/python/fastsim/demos/demo_param_paths.py b/python/fastsim/demos/demo_variable_paths.py similarity index 73% rename from python/fastsim/demos/demo_param_paths.py rename to python/fastsim/demos/demo_variable_paths.py index 0fd52f37..7551e8a8 100644 --- a/python/fastsim/demos/demo_param_paths.py +++ b/python/fastsim/demos/demo_variable_paths.py @@ -1,11 +1,9 @@ -# %% -import fastsim as fsim - -# %% [markdown] +""" +Script demonstrating how to use variable_path_list() and history_path_list() +demos to find the paths to variables within fastsim classes. +""" -# `fastsim3` -- load vehicle, cycle and simdrive, and demonstrate usage of methods -# `param_path_list()` and `history_path_list()` -# %% +import fastsim as fsim # load 2012 Ford Fusion from file veh = fsim.Vehicle.from_file( @@ -22,7 +20,7 @@ sd = fsim.SimDrive(veh, cyc) # print out all subpaths for variables in SimDrive -print("List of variable paths for SimDrive: ", sd.param_path_list()) +print("List of variable paths for SimDrive: ", sd.variable_path_list()) # print out all subpaths for history variables in SimDrive print("List of history variable paths for SimDrive: ", sd.history_path_list()) \ No newline at end of file diff --git a/python/fastsim/tests/test_param_paths.py b/python/fastsim/tests/test_variable_paths.py similarity index 97% rename from python/fastsim/tests/test_param_paths.py rename to python/fastsim/tests/test_variable_paths.py index 565e99cd..6a903abf 100644 --- a/python/fastsim/tests/test_param_paths.py +++ b/python/fastsim/tests/test_variable_paths.py @@ -20,7 +20,7 @@ def test_param_path_list(self): 'fc.history.pwr_loss_watts', 'fc.history.eff', 'history', 'fc.history.i', 'fc.history.pwr_prop_max_watts', 'fc.history.pwr_tractive_watts', 'fc.history.energy_aux_joules', 'fc.history.pwr_fuel_watts', 'fc.history.energy_loss_joules', 'fc.history.fc_on', 'fc.history.pwr_aux_watts', 'fc.history.energy_tractive_joules', 'fc.history.energy_fuel_joules', 'fc.history.pwr_loss_watts', 'fc.history.eff', 'history'] - assert(baseline_variable_paths.sort()==veh.param_path_list().sort()) + assert(baseline_variable_paths.sort()==veh.variable_path_list().sort()) assert(baseline_history_variable_paths.sort()==veh.history_path_list().sort()) From 8b56e71cb671a4fd852c90a37f29b01b1d1a49b0 Mon Sep 17 00:00:00 2001 From: Robin Steuteville Date: Mon, 24 Jun 2024 09:09:49 -0400 Subject: [PATCH 11/15] moving benchmark variable and history path lists to text files --- python/fastsim/__init__.py | 21 ++++++--- .../vehicle_history_paths.txt | 13 ++++++ .../vehicle_variable_paths.txt | 45 +++++++++++++++++++ python/fastsim/tests/test_variable_paths.py | 18 +++----- 4 files changed, 78 insertions(+), 19 deletions(-) create mode 100644 python/fastsim/resources/benchmark_variable_paths/vehicle_history_paths.txt create mode 100644 python/fastsim/resources/benchmark_variable_paths/vehicle_variable_paths.txt diff --git a/python/fastsim/__init__.py b/python/fastsim/__init__.py index 151a298d..81ad67a9 100644 --- a/python/fastsim/__init__.py +++ b/python/fastsim/__init__.py @@ -11,6 +11,14 @@ def package_root() -> Path: """Returns the package root directory.""" return Path(__file__).parent +def resources_root() -> Path: + """ + Returns the resources root directory. + """ + path = package_root() / "resources" + return path + + from pkg_resources import get_distribution __version__ = get_distribution("fastsim").version @@ -97,7 +105,8 @@ class (relative to the class the method was called on) See example usage in by user. Specifies a list of paths to be appended to the list returned by the method. """ - variable_list = [attr for attr in self.__dir__() if not attr.startswith("__") and not callable(getattr(self,attr))] + variable_list = [attr for attr in self.__dir__() if not attr.startswith("__")\ + and not callable(getattr(self,attr))] for variable in variable_list: if not type(getattr(self,variable)).__name__ in ACCEPTED_RUST_STRUCTS: if path == "": @@ -117,8 +126,10 @@ class (relative to the class the method was called on) See example usage in variable_path = variable else: variable_path = path + "." + variable - variable_path_list = getattr(self,variable).variable_path_list(path = variable_path,\ - variable_path_list = variable_path_list) + variable_path_list = getattr(self,variable).variable_path_list( + path = variable_path, + variable_path_list = variable_path_list, + ) return variable_path_list def history_path_list(self) -> List[str]: @@ -135,7 +146,5 @@ def history_path_list(self) -> List[str]: # adds variable_path_list() and history_path_list() as methods to all classes in # ACCEPTED_RUST_STRUCTS for item in ACCEPTED_RUST_STRUCTS: - print("starting", item) setattr(getattr(fsim, item), "variable_path_list", variable_path_list) - setattr(getattr(fsim, item), "history_path_list", history_path_list) - print(item, "finished!") \ No newline at end of file + setattr(getattr(fsim, item), "history_path_list", history_path_list) \ No newline at end of file diff --git a/python/fastsim/resources/benchmark_variable_paths/vehicle_history_paths.txt b/python/fastsim/resources/benchmark_variable_paths/vehicle_history_paths.txt new file mode 100644 index 00000000..f7bad438 --- /dev/null +++ b/python/fastsim/resources/benchmark_variable_paths/vehicle_history_paths.txt @@ -0,0 +1,13 @@ +fc.history.i +fc.history.pwr_prop_max_watts +fc.history.pwr_tractive_watts +fc.history.energy_aux_joules +fc.history.pwr_fuel_watts +fc.history.energy_loss_joules +fc.history.fc_on +fc.history.pwr_aux_watts +fc.history.energy_tractive_joules +fc.history.energy_fuel_joules +fc.history.pwr_loss_watts +fc.history.eff +history diff --git a/python/fastsim/resources/benchmark_variable_paths/vehicle_variable_paths.txt b/python/fastsim/resources/benchmark_variable_paths/vehicle_variable_paths.txt new file mode 100644 index 00000000..a4c5abc6 --- /dev/null +++ b/python/fastsim/resources/benchmark_variable_paths/vehicle_variable_paths.txt @@ -0,0 +1,45 @@ +fc.eff_min +fc.pwr_out_frac_interp +fc.pwr_ramp_lag_seconds +fc.pwr_ramp_lag_hours +fc.pwr_idle_fuel_watts +fc.mass_kg +fc.eff_range +fc.state.pwr_loss_watts +fc.state.pwr_tractive_watts +fc.state.pwr_aux_watts +fc.state.pwr_fuel_watts +fc.state.energy_fuel_joules +fc.state.energy_tractive_joules +fc.state.eff +fc.state.energy_loss_joules +fc.state.energy_aux_joules +fc.state.fc_on +fc.state.pwr_prop_max_watts +fc.state.i +fc.eff_max +fc.specific_pwr_kw_per_kg +fc.pwr_out_max_watts +fc.history.i +fc.history.pwr_prop_max_watts +fc.history.pwr_tractive_watts +fc.history.energy_aux_joules +fc.history.pwr_fuel_watts +fc.history.energy_loss_joules +fc.history.fc_on +fc.history.pwr_aux_watts +fc.history.energy_tractive_joules +fc.history.energy_fuel_joules +fc.history.pwr_loss_watts +fc.history.eff +fc.pwr_out_max_init_watts +fc.eff_interp +fc.save_interval +pwr_aux_watts +trans_eff +state +chassis +year +save_interval +history +name \ No newline at end of file diff --git a/python/fastsim/tests/test_variable_paths.py b/python/fastsim/tests/test_variable_paths.py index 6a903abf..13801e65 100644 --- a/python/fastsim/tests/test_variable_paths.py +++ b/python/fastsim/tests/test_variable_paths.py @@ -7,19 +7,11 @@ def test_param_path_list(self): veh = fsim.Vehicle.from_file( str(fsim.package_root() / "../../tests/assets/2012_Ford_Fusion.yaml") ) - baseline_variable_paths = ['fc.eff_min', 'fc.pwr_out_frac_interp', 'fc.pwr_ramp_lag_seconds', 'fc.pwr_ramp_lag_hours', 'fc.pwr_idle_fuel_watts', 'fc.mass_kg', 'fc.eff_range', - 'fc.state.pwr_loss_watts', 'fc.state.pwr_tractive_watts', 'fc.state.pwr_aux_watts', 'fc.state.pwr_fuel_watts', 'fc.state.energy_fuel_joules', - 'fc.state.energy_tractive_joules', 'fc.state.eff', 'fc.state.energy_loss_joules', 'fc.state.energy_aux_joules', 'fc.state.fc_on', - 'fc.state.pwr_prop_max_watts', 'fc.state.i', 'fc.eff_max', 'fc.specific_pwr_kw_per_kg', 'fc.pwr_out_max_watts', 'fc.history.i', - 'fc.history.pwr_prop_max_watts', 'fc.history.pwr_tractive_watts', 'fc.history.energy_aux_joules', 'fc.history.pwr_fuel_watts', - 'fc.history.energy_loss_joules', 'fc.history.fc_on', 'fc.history.pwr_aux_watts', 'fc.history.energy_tractive_joules', 'fc.history.energy_fuel_joules', - 'fc.history.pwr_loss_watts', 'fc.history.eff', 'fc.pwr_out_max_init_watts', 'fc.eff_interp', 'fc.save_interval', 'pwr_aux_watts', 'trans_eff', 'state', - 'chassis', 'year', 'save_interval', 'history', 'name'] - baseline_history_variable_paths = ['fc.history.i', 'fc.history.pwr_prop_max_watts', 'fc.history.pwr_tractive_watts', 'fc.history.energy_aux_joules', 'fc.history.pwr_fuel_watts', - 'fc.history.energy_loss_joules', 'fc.history.fc_on', 'fc.history.pwr_aux_watts', 'fc.history.energy_tractive_joules', 'fc.history.energy_fuel_joules', - 'fc.history.pwr_loss_watts', 'fc.history.eff', 'history', 'fc.history.i', 'fc.history.pwr_prop_max_watts', 'fc.history.pwr_tractive_watts', - 'fc.history.energy_aux_joules', 'fc.history.pwr_fuel_watts', 'fc.history.energy_loss_joules', 'fc.history.fc_on', 'fc.history.pwr_aux_watts', - 'fc.history.energy_tractive_joules', 'fc.history.energy_fuel_joules', 'fc.history.pwr_loss_watts', 'fc.history.eff', 'history'] + with open(fsim.resources_root() / "benchmark_variable_paths/vehicle_variable_paths.txt") as file: + baseline_variable_paths = file.readlines() + with open(fsim.resources_root() / "benchmark_variable_paths/vehicle_history_paths.txt") as file: + baseline_history_variable_paths = file.readlines() + assert(baseline_variable_paths.sort()==veh.variable_path_list().sort()) assert(baseline_history_variable_paths.sort()==veh.history_path_list().sort()) From b0624043120c9af355b1a66e069295c447c6c609 Mon Sep 17 00:00:00 2001 From: Robin Steuteville Date: Tue, 25 Jun 2024 17:03:50 -0400 Subject: [PATCH 12/15] fixing problem with history function --- python/fastsim/__init__.py | 24 ++++++++------------- python/fastsim/tests/test_variable_paths.py | 9 ++++---- 2 files changed, 14 insertions(+), 19 deletions(-) diff --git a/python/fastsim/__init__.py b/python/fastsim/__init__.py index 81ad67a9..563b7cf5 100644 --- a/python/fastsim/__init__.py +++ b/python/fastsim/__init__.py @@ -92,45 +92,39 @@ def __array__(self): attr[0].isupper() and\ ("fastsim" in str(inspect.getmodule(getattr(fsim,attr))))] -def variable_path_list(self, path = "", variable_path_list = []) -> List[str]: +def variable_path_list(self, path = "") -> List[str]: """Returns list of relative paths to all variables and sub-variables within - class (relative to the class the method was called on) See example usage in - demo_param_paths.py. + class (relative to the class the method was called on). + See example usage in demo_param_paths.py. Arguments: ---------- path : Defaults to empty string. This is mainly used within the method in order to call the method recursively and should not be specified by user. - Specifies a path to be added in front of all paths returned by the method. - variable_path_list : Defaults to empty list. This is mainly used within the - method in order to call the method recursively and should not be specified - by user. Specifies a list of paths to be appended to the list returned by - the method. + Specifies a path to be added in front of all paths returned by the method. """ variable_list = [attr for attr in self.__dir__() if not attr.startswith("__")\ and not callable(getattr(self,attr))] + variable_paths = [] for variable in variable_list: if not type(getattr(self,variable)).__name__ in ACCEPTED_RUST_STRUCTS: if path == "": variable_path = variable else: variable_path = path + "." + variable - variable_path_list.append(variable_path) + variable_paths.append(variable_path) elif len([attr for attr in getattr(self,variable).__dir__() if not attr.startswith("__")\ and not callable(getattr(getattr(self,variable),attr))]) == 0: if path == "": variable_path = variable else: variable_path = path + "." + variable - variable_path_list.append(variable_path) + variable_paths.append(variable_path) else: if path == "": variable_path = variable else: variable_path = path + "." + variable - variable_path_list = getattr(self,variable).variable_path_list( - path = variable_path, - variable_path_list = variable_path_list, - ) - return variable_path_list + variable_paths.extend(getattr(self,variable).variable_path_list(path = variable_path)) + return variable_paths def history_path_list(self) -> List[str]: """Returns a list of relative paths to all history variables (all variables diff --git a/python/fastsim/tests/test_variable_paths.py b/python/fastsim/tests/test_variable_paths.py index 13801e65..7ceb1d61 100644 --- a/python/fastsim/tests/test_variable_paths.py +++ b/python/fastsim/tests/test_variable_paths.py @@ -8,12 +8,13 @@ def test_param_path_list(self): str(fsim.package_root() / "../../tests/assets/2012_Ford_Fusion.yaml") ) with open(fsim.resources_root() / "benchmark_variable_paths/vehicle_variable_paths.txt") as file: - baseline_variable_paths = file.readlines() + baseline_variable_paths = [line.strip() for line in file.readlines()] + with open(fsim.resources_root() / "benchmark_variable_paths/vehicle_history_paths.txt") as file: - baseline_history_variable_paths = file.readlines() + baseline_history_variable_paths = [line.strip() for line in file.readlines()] - assert(baseline_variable_paths.sort()==veh.variable_path_list().sort()) - assert(baseline_history_variable_paths.sort()==veh.history_path_list().sort()) + assert(sorted(baseline_variable_paths)==sorted(veh.variable_path_list())) + assert(sorted(baseline_history_variable_paths)==sorted(veh.history_path_list())) if __name__ == '__main__': From ae87ed90509838229cbd78ed6ff29f96aeba9a23 Mon Sep 17 00:00:00 2001 From: Robin Steuteville Date: Wed, 26 Jun 2024 15:53:29 -0400 Subject: [PATCH 13/15] updating formattng for demo file' --- python/fastsim/demos/demo_variable_paths.py | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/python/fastsim/demos/demo_variable_paths.py b/python/fastsim/demos/demo_variable_paths.py index 7551e8a8..e4861395 100644 --- a/python/fastsim/demos/demo_variable_paths.py +++ b/python/fastsim/demos/demo_variable_paths.py @@ -20,7 +20,7 @@ sd = fsim.SimDrive(veh, cyc) # print out all subpaths for variables in SimDrive -print("List of variable paths for SimDrive: ", sd.variable_path_list()) +print("List of variable paths for SimDrive:\n", "\n".join(sd.variable_path_list())) # print out all subpaths for history variables in SimDrive -print("List of history variable paths for SimDrive: ", sd.history_path_list()) \ No newline at end of file +print("List of history variable paths for SimDrive:\n", "\n".join(sd.history_path_list())) \ No newline at end of file From a44a6b22f20fc1a67d2a0bf0b2f736dd1670e85e Mon Sep 17 00:00:00 2001 From: Robin Steuteville Date: Wed, 26 Jun 2024 16:11:29 -0400 Subject: [PATCH 14/15] updating function doc strings --- python/fastsim/__init__.py | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/python/fastsim/__init__.py b/python/fastsim/__init__.py index 563b7cf5..40eaaa98 100644 --- a/python/fastsim/__init__.py +++ b/python/fastsim/__init__.py @@ -95,7 +95,7 @@ def __array__(self): def variable_path_list(self, path = "") -> List[str]: """Returns list of relative paths to all variables and sub-variables within class (relative to the class the method was called on). - See example usage in demo_param_paths.py. + See example usage in `fastsim/demos/demo_variable_paths.py`. Arguments: ---------- path : Defaults to empty string. This is mainly used within the method in order to call the method recursively and should not be specified by user. @@ -129,7 +129,7 @@ class (relative to the class the method was called on). def history_path_list(self) -> List[str]: """Returns a list of relative paths to all history variables (all variables that contain history as a subpath). - See example usage in demo_param_paths.py.""" + See example usage in `fastsim/demos/demo_variable_paths.py`.""" return [item for item in self.variable_path_list() if "history" in item] From f1d2941190355e9f1e1e907727095a66a837a7ff Mon Sep 17 00:00:00 2001 From: Chad Baker Date: Thu, 11 Jul 2024 14:46:51 -0600 Subject: [PATCH 15/15] switched to using prius to test more components updated path based on Kyle's changes turned off some getters/setters because they trigger `todo!()` --- .../powertrain/reversible_energy_storage.rs | 32 +++++------ fastsim-core/src/vehicle/vehicle_model.rs | 57 +++++++++---------- python/fastsim/demos/demo_variable_paths.py | 5 +- 3 files changed, 47 insertions(+), 47 deletions(-) diff --git a/fastsim-core/src/vehicle/powertrain/reversible_energy_storage.rs b/fastsim-core/src/vehicle/powertrain/reversible_energy_storage.rs index a03a8d75..7864bb9d 100644 --- a/fastsim-core/src/vehicle/powertrain/reversible_energy_storage.rs +++ b/fastsim-core/src/vehicle/powertrain/reversible_energy_storage.rs @@ -58,30 +58,30 @@ const TOL: f64 = 1e-3; Ok(()) } - #[getter("eff_max")] - fn get_eff_max_py(&self) -> f64 { - self.get_eff_max() - } + // #[getter("eff_max")] + // fn get_eff_max_py(&self) -> f64 { + // self.get_eff_max() + // } - #[setter("__eff_max")] - fn set_eff_max_py(&mut self, eff_max: f64) -> PyResult<()> { - self.set_eff_max(eff_max).map_err(PyValueError::new_err) - } + // #[setter("__eff_max")] + // fn set_eff_max_py(&mut self, eff_max: f64) -> PyResult<()> { + // self.set_eff_max(eff_max).map_err(PyValueError::new_err) + // } - #[getter("eff_min")] - fn get_eff_min_py(&self) -> f64 { - self.get_eff_min() - } + // #[getter("eff_min")] + // fn get_eff_min_py(&self) -> f64 { + // self.get_eff_min() + // } #[getter("eff_range")] fn get_eff_range_py(&self) -> f64 { self.get_eff_range() } - #[setter("__eff_range")] - fn set_eff_range_py(&mut self, eff_range: f64) -> anyhow::Result<()> { - self.set_eff_range(eff_range) - } + // #[setter("__eff_range")] + // fn set_eff_range_py(&mut self, eff_range: f64) -> anyhow::Result<()> { + // self.set_eff_range(eff_range) + // } // TODO: decide on way to deal with `side_effect` coming after optional arg and uncomment #[pyo3(name = "set_mass")] diff --git a/fastsim-core/src/vehicle/vehicle_model.rs b/fastsim-core/src/vehicle/vehicle_model.rs index 26e26c4a..fd306fe4 100644 --- a/fastsim-core/src/vehicle/vehicle_model.rs +++ b/fastsim-core/src/vehicle/vehicle_model.rs @@ -42,42 +42,41 @@ impl Init for AuxSource {} fn set_fc_py(&mut self, _fc: FuelConverter) -> PyResult<()> { Err(PyAttributeError::new_err(DIRECT_SET_ERR)) } - - #[setter(__fc)] + #[setter("__fc")] fn set_fc_hidden(&mut self, fc: FuelConverter) -> PyResult<()> { self.set_fc(fc).map_err(|e| PyAttributeError::new_err(e.to_string())) } - // #[getter] - // fn get_res(&self) -> Option { - // self.reversible_energy_storage().cloned() - // } - // #[setter] - // fn set_res(&mut self, _res: ReversibleEnergyStorage) -> PyResult<()> { - // Err(PyAttributeError::new_err(DIRECT_SET_ERR)) - // } + #[getter] + fn get_res(&self) -> Option { + self.res().cloned() + } + #[setter("res")] + fn set_res_py(&mut self, _res: ReversibleEnergyStorage) -> PyResult<()> { + Err(PyAttributeError::new_err(DIRECT_SET_ERR)) + } + #[setter("__res")] + fn set_res_hidden(&mut self, res: ReversibleEnergyStorage) -> PyResult<()> { + self.set_res(res).map_err(|e| PyAttributeError::new_err(e.to_string())) + } - // #[setter(__res)] - // fn set_res_hidden(&mut self, res: ReversibleEnergyStorage) -> PyResult<()> { - // self.set_reversible_energy_storage(res).map_err(|e| PyAttributeError::new_err(e.to_string())) - // } - // #[getter] - // fn get_em(&self) -> ElectricMachine { - // self.em().clone() - // } + #[getter] + fn get_em(&self) -> Option { + self.em().cloned() + } - // #[setter] - // fn set_em_py(&mut self, _em: ElectricMachine) -> PyResult<()> { - // Err(PyAttributeError::new_err(DIRECT_SET_ERR)) - // } - // #[setter(__em)] - // fn set_em_hidden(&mut self, em: ElectricMachine) -> PyResult<()> { - // self.set_em(em).map_err(|e| PyAttributeError::new_err(e.to_string())) - // } + #[setter("em")] + fn set_em_py(&mut self, _em: ElectricMachine) -> PyResult<()> { + Err(PyAttributeError::new_err(DIRECT_SET_ERR)) + } + #[setter("__em")] + fn set_em_hidden(&mut self, em: ElectricMachine) -> PyResult<()> { + self.set_em(em).map_err(|e| PyAttributeError::new_err(e.to_string())) + } - // fn veh_type(&self) -> PyResult { - // Ok(self.pt_type.to_string()) - // } + fn veh_type(&self) -> PyResult { + Ok(self.pt_type.to_string()) + } // #[getter] // fn get_pwr_rated_kilowatts(&self) -> f64 { diff --git a/python/fastsim/demos/demo_variable_paths.py b/python/fastsim/demos/demo_variable_paths.py index e4861395..e810089e 100644 --- a/python/fastsim/demos/demo_variable_paths.py +++ b/python/fastsim/demos/demo_variable_paths.py @@ -7,20 +7,21 @@ # load 2012 Ford Fusion from file veh = fsim.Vehicle.from_file( - str(fsim.package_root() / "../../tests/assets/2012_Ford_Fusion.yaml") + str(fsim.package_root() / "../../tests/assets/2016_TOYOTA_Prius_Two.yaml") ) # Set `save_interval` at vehicle level -- cascades to all sub-components with time-varying states veh.save_interval = 1 # load cycle from file -cyc = fsim.Cycle.from_resource("cycles/udds.csv") +cyc = fsim.Cycle.from_resource("udds.csv") # instantiate `SimDrive` simulation object sd = fsim.SimDrive(veh, cyc) # print out all subpaths for variables in SimDrive print("List of variable paths for SimDrive:\n", "\n".join(sd.variable_path_list())) +print("\n") # print out all subpaths for history variables in SimDrive print("List of history variable paths for SimDrive:\n", "\n".join(sd.history_path_list())) \ No newline at end of file