homepage tests release python documentation github

Description

This is the fastsim-3 version of NREL's FASTSim. It introduces numerous new enhancements and features, including:

  • ~10x faster! -- when setting save_interval to None, which means only the state at the last time step, which includes fuel consumption and/or battery depletion, among other useful cumulative state variables.
  • Roughly ~60% reduction in memory consumption (~160 mb in fastsim-2 v. 60 mb in fastsim-3
  • object-oriented, hierarchical model structure
  • ability to control granularity of time-resolved data -- e.g. save at every time step, save at every _n_th time step, or never save at all (saving only cumulative trip-level results)
  • component-specific vehicle models -- i.e. the conventional vehicle contains only data for the fuel converter and other relevant components but does contain any dummy battery or motor parameters as is the case in fastsim-2
  • file formats that are more robust and more human readable
  • backwards compatibility with fastsim-2
  • flexible data structures to allow for future model types
  • ability to simulate standalone component models
  • flexible model interfacing (e.g. multiple folder/file formats for reading and/or writing data)
  • more accurate interpolation methods

Installation

Python

Set up and activate a python environment (compatible with Python 3.8 - 3.10; we recommend Python 3.10) with the following steps.

Anaconda

  1. Create: conda create -n fastsim python=3.10
  2. Activate: conda activate fastsim

venv

There is some variation based on your Operating System:

  • PowerShell (windows):

    1. Create: python -m venv fastsim-venv -- name is user decision
    2. Activate: fastsim-venv/Scripts/Activate.ps1
  • Bash (i.e. unix/linux/mac):

    1. Create: python -m venv fastsim-venv -- name is user decision
    2. Activate: source fastsim-venv/bin/activate
  • Command Prompt (windows):

    1. Create: python -m venv fastsim-venv -- name is user decision
    2. Activate: fastsim-venv/Scripts/activate.bat
  1. pixi shell -e dev -- this creates the environment, installs all the dependencies, builds fastsim, and activates the environment

FASTSim-3

Via PyPI

In an active Python environment created above, run pip install fastsim.

Building from Scratch

Developers might want to install the code in place so that FASTSim files can be editable (the -e flag for pip provides this behavior). This option can be handy since FASTSim will be installed in place from the installation location and any updates will be propagated each time FASTSim is freshly imported. To do this, you'll need to have the Rust toolchain installed.

  • Option 1: run sh build_and_test.sh in root folder.
  • Option 2:
    1. Run pip install -e ".[dev]"
      Optional testing steps:
    2. Run cargo test
    3. Run pytest -v python/fastsim/tests/

Contributors

Chad Baker -- Chad.Baker@nrel.gov
Aaron Brooker -- Aaron.Brooker@nrel.gov
Kyle Carow -- Kyle.Carow@nrel.gov
Jeffrey Gonder -- Jeff.Gonder@nrel.gov
Jacob Holden -- Jacob.Holden@nrel.gov
Jinghu Hu -- Jinghu.Hu@nrel.gov
Jason Lustbader -- Jason.Lustbader@nrel.gov
Sean Lopp -- sean@rstudio.com
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

About this book

This is the overall FASTSim documentation. We're working toward making this a fully integrated document that includes both the Python API and Rust core documentation for the fastsim-2 branch and eventually also for the fastsim-3 branch.

Documentation

Python

Rust

Developers

Table of Contents

fastsim

Python API for fastsim

check_version_gte_311

def check_version_gte_311() -> bool

Return true if python version is greater than or equal to 3.11

package_root

def package_root() -> Path

Return the package root directory.

resources_root

def resources_root() -> Path

Return the resources root directory.

cyc_keys

def cyc_keys() -> list[str]

Return cycle keys

to_pydict

def to_pydict(self, data_fmt: str = "msg_pack", flatten: bool = False) -> dict

Return self converted to pure python dictionary with no nested Rust objects

Arguments

  • - flatten: if True, returns dict without any hierarchy
  • - data_fmt: data format for intermediate conversion step

get_hist_len

def get_hist_len(obj: dict) -> int | None

Find nested history and gets lenth of first element

get_flattened

def get_flattened(obj: dict | list,
                  hist_len: int,
                  prepend_str: str = "") -> dict

Flatten and return dictionary, separating keys and indices with a "."

Arguments

- obj: object to flatten

- hist_len: length of any lists storing history data

- prepend_str: prepend this to all keys in the returned flat dict

from_pydict

@classmethod
def from_pydict(cls,
                pydict: dict,
                data_fmt: str = "msg_pack",
                skip_init: bool = False) -> Self

Instantiate Self from pure python dictionary

Arguments

  • - pydict: dictionary to be converted to FASTSim object
  • - data_fmt: data format for intermediate conversion step
  • - skip_init: passed to SerdeAPI methods to control whether initialization is skipped

to_dataframe

def to_dataframe(self,
                 pandas: bool = False,
                 allow_partial: bool = False) -> pd.DataFrame | pl.DataFrame

Return time series results from fastsim object as a Polars or Pandas dataframe.

Arguments

  • - pandas: returns pandas dataframe if True; otherwise, returns polars dataframe by default
  • - allow_partial: tries to return dataframe of length equal to solved time steps if simulation fails early

fastsim.utils.utilities

copy_demo_files

def copy_demo_files(path_for_copies: Path = Path("demos"))

Copies demo files from demos folder into specified local directory Arguments

  • - path_for_copies: path to copy files into (relative or absolute in) Warning

Running this function will overwrite existing files with the same name in the specified directory, so make sure any files with changes you'd like to keep are renamed.

fastsim.utils

fastsim.copy_stub_docstrings

fastsim.pymoo_api

Module containing functions and classes for easy interaction with PyMOO

get_error_val

def get_error_val(model: npt.NDArray[np.float64],
                  test: npt.NDArray[np.float64],
                  time_steps: npt.NDArray[np.float64]) -> float

Returns time-averaged error for model and test signal.

Args:

  • model: array of values for signal from model
  • test: array of values for signal from test data
  • time_steps: array (or scalar for constant) of values for model time steps [s]

Returns:

  • error: integral of absolute value of difference between model and test per time

ModelObjectives Objects

@dataclass
class ModelObjectives()

Class for calculating eco-driving objectives

Attributes/Fields

  • models (Dict[str, Dict]): dictionary of model dicts to be simulated
  • dfs (Dict[str, pd.DataFrame]): dictionary of dataframes from test data corresponding to models
  • obj_fns (Tuple[Callable] | Tuple[Tuple[Callable, Callable]]): Tuple of functions for extracting objective signal values for either minimizing a scalar metric (e.g. fuel economy) or minimizing error relative to test data.
    • minimizing error in fuel consumption relative to test data
      obj_fns = (
          (
              # model -- note, `lambda` only works for single thread
              lambda sd_dict: sd_dict['veh']['pt_type']['Conventional']['fc']['history']['energy_fuel_joules'],
              # test data
              lambda df: df['fuel_flow_gps'] * ... (conversion factors to get to same unit),
          ), # note that this trailing comma ensures `obj_fns` is interpreted as a tuple
      )
      
    • minimizing fuel consumption
      obj_fns = (
          (
              # note that a trailing comma ensures `obj_fns` is interpreted as tuple
              lambda sd_dict: sd_dict['veh']['pt_type']['Conventional']['fc']['state']['energy_fuel_joules'],
          )
      )
      
  • param_fns_and_bounds Tuple[Tuple[Callable], Tuple[Tuple[float, float]]]: tuple containing functions to modify parameters and bounds for optimizer Example
    def new_peak_res_eff (sd_dict, new_peak_eff) -> Dict:
        sd_dict['veh']['pt_type']['HybridElectricVehicle']['res']['peak_eff'] = new_peak_eff
        return sd_dict
    ...
    param_fns_and_bounds = (
        (new_peak_res_eff, (100.0, 200.0)),
    )
    
  • verbose (bool): print more stuff or not

update_params

def update_params(xs: list[Any])

Updates model parameters based on x, which must match length of self.param_fns

get_errors

def get_errors(
    sim_drives: dict[str, fsim.SimDrive],
    return_mods: bool = False
) -> (tuple[dict[str, list[float]], dict[str, list[float]]]
      | tuple[
          dict[str, list[float]],
          dict[str, list[float]],
          dict[str, fsim.SimDrive | Any],
          dict[str, fsim.SimDrive | Any],
      ])

Calculate model errors w.r.t. test data for each element in dfs/models for each objective.

Args:

  • sim_drives: dictionary with user-defined keys and SimDrive instances
  • return_mods: if true, also returns dict of solved models. Defaults to False.

Returns:

Objectives and optionally solved models

get_parser

def get_parser(
        def_description: str = "Program for calibrating fastsim models.",
        def_p: int = 4,
        def_n_max_gen: int = 500,
        def_pop_size: int = 12) -> argparse.ArgumentParser

Generate parser for optimization hyper params and misc. other params

Args:

  • def_p: default number of processes
  • def_n_max_gen: max allowed generations
  • def_pop_size: default population size

Returns:

argparse.ArgumentParser: description

fastsim.tests.test_speedup

fastsim.tests.test_serde

fastsim.tests.test_utils

fastsim.tests.test_resources

Test getting resource lists via Rust API

test_list_resources_for_cycle

def test_list_resources_for_cycle()

Assert list_resources works for Cycle

test_list_resources_for_vehicle

def test_list_resources_for_vehicle()

Assert list_resources works for Vehicle

fastsim.demos.demo_hev

Hybrid electric vehicle demo showcasing FASTSim-3 simulation capabilities.

plot_road_loads_comparison

def plot_road_loads_comparison() -> tuple[Figure, Axes]

Plot comparison of fastsim-3 v. fastsim-2 road loads

plot_fc_pwr

def plot_fc_pwr() -> tuple[Figure, Axes]

Plot fuel converter powers

plot_fc_energy

def plot_fc_energy() -> tuple[Figure, Axes]

Plot fuel converter energies

plot_res_pwr

def plot_res_pwr() -> tuple[Figure, Axes]

Plot reversible energy storage powers

plot_res_energy

def plot_res_energy() -> tuple[Figure, Axes]

Plot reversible energy storage energies

fastsim.demos.test_demos

Test suite for FASTSim demo scripts to ensure they run without errors.

demo_paths

def demo_paths()

Get list of all demo script paths.

test_demo

@pytest.mark.parametrize("demo_path",
                         demo_paths(),
                         ids=[dp.name for dp in demo_paths()])
def test_demo(demo_path: Path)

Test that each demo script runs successfully without errors.

fastsim.demos.plot_utils

Plotting utilities for FASTSim demo scripts.

get_paired_cycler

def get_paired_cycler(pair_attr: str = DEF_PAIR_ATTR)

Return a cycler for setting style in paired plots

Arguments:

  • pair_attr: whether the paired lines should match in "color" or "linestyle"

get_uni_cycler

def get_uni_cycler(pair_attr: str = DEF_PAIR_ATTR)

Get a uniform cycler for plotting.

Arguments:

  • pair_attr: ensures consistent behavior with get_paired_cycler

plot_bev_temperatures

def plot_bev_temperatures(df: pd.DataFrame, save_figs: bool,
                          show_plots: bool) -> tuple[Figure, Axes]

Plot BEV component temperatures over time.

plot_bev_hvac_pwr

def plot_bev_hvac_pwr(df: pd.DataFrame, save_figs: bool,
                      show_plots: bool) -> tuple[Figure, Axes]

Plot BEV HVAC power consumption over time.

plot_bev_res_pwr

def plot_bev_res_pwr(df: pd.DataFrame, save_figs: bool,
                     show_plots: bool) -> tuple[Figure, Axes]

Plot BEV reversible energy storage power over time.

plot_bev_res_energy

def plot_bev_res_energy(df: pd.DataFrame, save_figs: bool,
                        show_plots: bool) -> tuple[Figure, Axes]

Plot BEV reversible energy storage energy over time.

plot_road_loads

def plot_road_loads(df: pd.DataFrame, veh: fsim.Vehicle, save_figs: bool,
                    show_plots: bool) -> tuple[Figure, Axes]

Plot vehicle road loads over time.

plot_hev_temperatures

def plot_hev_temperatures(df: pd.DataFrame, save_figs: bool,
                          show_plots: bool) -> tuple[Figure, Axes]

Plot HEV component temperatures including battery, engine, and cabin.

plot_hev_fc_pwr

def plot_hev_fc_pwr(df: pd.DataFrame, save_figs: bool,
                    show_plots: bool) -> tuple[Figure, Axes]

Plot HEV fuel converter powers

plot_hev_fc_energy

def plot_hev_fc_energy(df: pd.DataFrame, save_figs: bool,
                       show_plots: bool) -> tuple[Figure, Axes]

Plot HEV fuel converter energy consumption over time.

plot_hev_res_pwr

def plot_hev_res_pwr(df: pd.DataFrame, save_figs: bool,
                     show_plots: bool) -> tuple[Figure, Axes]

Plot HEV reversible energy storage power including electrical and thermal.

plot_hev_res_energy

def plot_hev_res_energy(df: pd.DataFrame, save_figs: bool,
                        show_plots: bool) -> tuple[Figure, Axes]

Plot HEV reversible energy storage energy including electrical and thermal.

fastsim.demos.demo_bev_thrml_sweep

BEV thermal demo with cold start and cold ambient conditions.

try_walk

def try_walk(sd: fsim.SimDrive, loc: str) -> None

Wrap walk in try to enable context

setup_sweep

def setup_sweep() -> pd.DataFrame

Set up sweep of ambient and initial conditions

sweep

def sweep(df: pd.DataFrame,
          n_proc: int | None) -> tuple[pd.DataFrame, pd.DataFrame]

Sweep ambient and initial conditions

Arguments:

- df: dataframe of DOE

- n_proc: number of parallel processes

solve_row

def solve_row(iterrow: tuple[Hashable, pd.Series]) -> dict[str, Any]

Solve row of dataframe and return result

plot_time_series

def plot_time_series(df: pd.DataFrame,
                     verbose: bool = False,
                     show_plots: bool = False,
                     save_figs: bool = False) -> None

Plot time series temperature data

plot_sweep

def plot_sweep(df: pd.DataFrame,
               cyc: str,
               x_var: str,
               par_var_sweep: list[float],
               show_plots: bool = False,
               save_figs: bool = False) -> tuple[plt.Figure, plt.Axes]

Plot sweep of ambient and initial temperatures, parameteric style

plot_sweep_cross_effects

def plot_sweep_cross_effects(
        df: pd.DataFrame,
        cyc: str,
        x_var: str,
        par_var_sweep: list[float],
        show_plots: bool = False,
        save_figs: bool = False) -> tuple[plt.Figure, plt.Axes]

Plot sweep of ambient and initial temperatures, parameteric style

def print_cross_delta(df: pd.DataFrame, cycle: str, fixed_var: str) -> None

Print percent increase in ECR for one variable when the other is fixed between 22C and 24C

fastsim.demos.demo_bev_thrml_ws_ca

BEV thermal demo with warm start and cold ambient conditions.

fastsim.demos.demo_trace_miss

A module that demonstrates trace-miss correction.

trace_miss_demo

def trace_miss_demo()

Run a vehicle over a cycle with a trace miss + correction

fastsim.demos.demo_bev

BEV demo showcasing FASTSim-3 vehicle simulation and plotting capabilities.

plot_res_pwr

def plot_res_pwr() -> tuple[Figure, Axes]

Plot reversible energy storage powers

plot_res_energy

def plot_res_energy() -> tuple[Figure, Axes]

Plot reversible energy storage energies

plot_road_loads_comparison

def plot_road_loads_comparison() -> tuple[Figure, Axes]

Plot comparison of fastsim-3 v. fastsim-2 road loads

test_this_file

def test_this_file()

To trigger automated testing

fastsim.demos.demo_hev_thrml_ws_ca

HEV thermal demo with warm start and cold ambient conditions.

fastsim.demos.demo_bev_thrml_ws_wa

BEV thermal demo with warm start and warm ambient conditions.

fastsim.demos.demo_hev_thrml_ws_wa

HEV thermal demo with warm start and warm ambient conditions.

fastsim.demos.demo_bev_thrml_cs_ca

BEV thermal demo with cold start and cold ambient conditions.

fastsim.demos.demo_cavs

Demonstration of Connected Automated Vehicle (CAV) Functionality in FASTSim

This module demonstrates:

  • cycle manipulation utilities
  • eco-approach: utilizing vehicle coasting to conserve fuel use
  • eco-cruise: use of trajectories to remove unnecessary accelerations

microtrip_demo

def microtrip_demo()

Run a demonstration of cycle manipulation utilities

plot_speed_by_time

def plot_speed_by_time(df,
                       c0,
                       is_coast=None,
                       save_interval=1,
                       title=None,
                       with_elevation=False)

Plot speed by time

plot_speed_by_dist

def plot_speed_by_dist(df,
                       c0,
                       is_coast=None,
                       save_interval=1,
                       title=None,
                       with_elevation=False)

Plot speed by distance

setup_models

def setup_models(cyc_file="udds.csv", veh_file="2012_Ford_Fusion.yaml")

Set up and return cycle and vehicle models

basic_coasting_demo

def basic_coasting_demo()

Demonstrate coasting starting from a given speed

advanced_coasting_demo

def advanced_coasting_demo()

Demonstrate coasting starting from a given speed

basic_cruise_demo

def basic_cruise_demo()

Demonstrate basic Eco-Cruise usage

cruise_and_coast_demo

def cruise_and_coast_demo()

Demonstrate both cruise and coast

coast_with_grade_demo

def coast_with_grade_demo()

Coasting in the presence of grade

fastsim.demos.demo_hev_thrml_cs_ca

HEV thermal demo with cold start and cold ambient conditions.

fastsim.demos.demo_conv

Conventional vehicle demo showcasing FASTSim-3 simulation capabilities.

plot_fc_pwr

def plot_fc_pwr() -> tuple[Figure, Axes]

Plot fuel converter powers

plot_fc_energy

def plot_fc_energy() -> tuple[Figure, Axes]

Plot fuel converter energies

plot_road_loads_comparison

def plot_road_loads_comparison() -> tuple[Figure, Axes]

Plot comparison of fastsim-3 v. fastsim-2 road loads

fastsim.demos

Rust Documentation

How to compile/test Rust code

cargo build

cargo build will not compile when run in /rust due to problems compiling /rust/fastsim-py. cargo build should compile when run in the /rust/fastsim-core.

cargo test

cargo test should compile when run in /rust because there are no tests in /rust/fastsim-py.

build_and_test.sh

Running sh build_and_test.sh from the root fastsim directory compile/tests the Rust code, and tests the Python code. It should compile without errors.

Releasing

Incrementing the Version Number

Increment the 3rd decimal place in the version number for small changes (e.g. minor bug fixes, new variables), the 2nd for medium changes (e.g. new methods or classes), and the 1st for large changes (e.g. changes to the interface that might affect backwards compatibility / the API interface).

Instructions

  1. Create and check out a new branch, e.g. for version X.X.X:
    git checkout -b fastsim-X.X.X
    
  2. Update the version number in the pyproject.toml file
  3. If changes have happened in rust/, increment the Rust crate version numbers in rust/fastsim-core/Cargo.toml and rust/fastsim-core/fastsim-proc-macros/Cargo.toml
  4. Commit changes, as appropriate:
    git add pyproject.toml README.md rust/fastsim-core/Cargo.toml rust/fastsim-core/fastsim-proc-macros/Cargo.toml
    
    git commit -m "vX.X.X"
    
  5. Tag the commit with the new version number, prepended with a v:
    git tag vX.X.X
    
    Or, optionally, you can also add a tag message with the -m flag, for example:
    git tag vX.X.X -m "release version X.X.X"
    
  6. Push the commit to the GitHub.com repository (for Git remote setup instructions, see this page):
    git push -u external fastsim-X.X.X
    
  7. Push the tag:
    git push external vX.X.X
    
    This will start the wheels.yaml GitHub Actions workflow and run all tests
  8. Create a PR for the new version in the external repository, using the release label for organization
  9. When all tests pass, and a review has been completed, merge the PR
  10. If changes were made in rust/, publish the crates (you must be listed as an owner of both crates on crates.io):
    If necessary, log into crates.io first after adding and verifying your email at https://crates.io/settings/profile:
    cargo login
    
    Then, run these commands to update the crates (order matters):
    (cd rust/fastsim-core/fastsim-proc-macros && cargo publish)
    (cd rust/fastsim-core && cargo publish)
    
  11. Start a new release at https://github.com/NREL/fastsim/releases/new, selecting vX.X.X as both the tag and the release name. Click "Generate release notes" to automatically create a detailed change log.
  12. Click "Publish release". Wheels will then be built for various platforms and automatically uploaded to the PyPI at https://pypi.org/project/fastsim/. Check that the release workflow finished properly at https://github.com/NREL/fastsim/actions/workflows/release.yaml!
  13. Synchronize changes to the internal GitHub repository:
    git pull external fastsim-2
    git push origin fastsim-2
    

Calibration and Validation of Vehicle Models

FASTSim powertrain models can have varying levels of calibration and resolution based on available calibration and validation data. In the simplest (US) cases, the only available validation data for a powertrain model is the EPA "window sticker" energy consumption rates. However, there are also situations in which detailed dynamometer or on-road data is available for a particular vehicle, enabling much more detailed model calibration. This documentation is meant to summarize these various calibration levels and the tools available to help with more detailed calibration.

Calibration/Validation Levels

LevelCalibrationValidation
0Vehicle is parameterized without any fitting to performance data. This is called parameterization, not calibration.Could be none or could be validated against aggregate energy consumption data like EPA window sticker values.
1Vehicle parameters are adjusted so that model results reasonably match test data for aggregate, cycle-level data (e.g. fuel usage, net SOC change).Model results reasonably match at least some aggregate, cycle-level test data not used in any calibration process.
2Vehicle parameters are adjusted so that model results reasonably match test data for time-resolved test data (e.g. instantaneous fuel usage, instantaneous cumulative fuel usage, instantaneous SOC).Model results reasonably match at least some time-resolved test data not used in any calibration process.
3Some amount of component-level thermal modeling is included and vehicle parameters are adjusted so that model results reasonably match test data for time-resolved test data (e.g. instantaneous fuel usage, instantaneous cumulative fuel usage, instantaneous SOC).Model results reasonably match time-resolved test data not used in any calibration process that covers various temperatures and/vehcile transient thermal states.

Examples of calibration levels 0, 2, and 3 from the FASTSim Validation Report:

image

image

image

Calibration Level 0 (Parameterization) Guidelines

As noted in the table above, parameterization of a new FASTSim powertrain model is performed when little or no ground truth performance data is available for a specific vehicle. One example of this is if EPA window-sticker fuel economy is the only available performance data. In this situation, it is recommended to parameterize a FASTSim powertrain model using the most reliable vehicle parameters from available information (e.g., specification websites). This helps to avoid overfitting and relies on the robustness of the FASTSim approach to capture the most important powertrain dynamics and simulate energy consumption.

  • Create a new vehicle file, either from a template or an existing vehicle model (ideally of the same powertrain type)
  • Enter vehicle parameters from various specification sources (note: it is recommended to document the source of specifications that are used to determine each parameter)
    • veh_pt_type and fc_eff_type are important high level descriptors that define the powertrain technology
      • veh_pt_type: Vehicle powertrain type
        • Parameter values:
          • Conv: conventional (ICE, gasoline or diesel) vehicle
          • HEV: hybrid electric vehicle
          • PHEV: plug-in hybrid electric vehicle
          • BEV: battery electric vehicle
      • fc_eff_type: Fuel converter efficiency type
        • This parameter is used to retrieve the default fc_eff_map for a particular engine type if a custom map is not provided
        • Unnecessary and not used for vehicles without a fuel converter (e.g. BEVs)
        • Parameter values:
          • SI: spark ignition
          • Atkinson: Atkinson cycle (typical for hybrids)
          • Diesel: diesel (compression ignition)
          • H2FC: hydrogen fuel cell (use with veh_pt_type set to HEV)
          • HD_Diesel: heavy-duty diesel
    • veh_override_kg is the simplest way to specify total vehicle mass
      • If not provided, the various component mass parameters will be used to calculate total vehicle mass
      • If veh_override_kg is provided, component mass parameters are unnecessary and not used
    • drag_coef and wheel_rr_coef can be calculated from dynamometer road load equation coefficients (ABCs) for vehicles tested by the US EPA using fastsim.auxiliaries.abc_to_drag_coeffs. Test data, including the road load coefficients from coast-down testing, for cars tested by the US EPA is available here.
      • drag_coef is sometimes provided on specification websites and reasonable values informed by engineering judgement for wheel_rr_coef can be used , but when possible the ABCs and fastsim.auxiliaries.abc_to_drag_coeffs method should be used instead
    • wheel_radius_m is often not explicitly available for a vehicle, but a tire code can be supplied to fastsim.utils.calculate_tire_radius to calculate a radius
    • Note: For hybrids, 'total system power' is often provided (e.g., combined ICE and electric motor powers). This should not be used for either fc_max_kw or mc_max_kw, peak engine-only power should be used for fc_max_kw and peak electric motor-only power for mc_max_kw.

Calibration Level 2 Guidelines

  • Copy calibration_demo.py to your project directory and modify as needed.
  • By default, this script selects the model that minimizes the euclidean error across all objectives, which may not be the way that you want to select your final design. By looking at the plots that get generated in save_path, you can use both the time series and parallel coordinates plots to down select an appropriate design.
  • Because PyMOO is a multi-objective optimizer that finds a multi-dimensional Pareto surface, it will not necessarily return a single best result -- rather, it will produce a pareto-optimal set of results, and you must down select. Often, the design with minimal euclidean error will be the best design, but it's good to pick a handful of designs from the pareto set and check how they behave in the time-resolved plots that can be optionally generated by the optimization script.
  • Run python calibration_demo.py --help to see details about how to run calibration and validation. Greater population size typically results in faster convergence at the expense of increased run time for each generation. There's no benefit in having a number of processes larger than the population size. xtol and ftol (see CLI help) can be used to adjust when the minimization is considered converged. If the optimization is terminating when n_max_gen is hit, then that means it has not converged, and you may want to increase n_max_gen.
  • Usually, start out with an existing vehicle model that is reasonably close to the new vehicle, and make sure to provide as many explicit parameters as possible. In some cases, a reasonable engineering judgment is appropriate.
  • Resample data to 1 Hz. This is a good idea because higher frequency data will cause fastsim to run more slowly. This can be done with fastsim.resample.resample. Be sure to specify rate_vars (e.g. fuel power flow rate [W]), which will be time averaged over the previous time step in the new frequency.
  • Identify test data signals and corresponding fastsim signals that need to match. These pairs of signals will be used to construct minimization objectives. See where obj_names is defined in calibration_demo.py for an example.
  • See where cycs[key] gets assigned to see an example of constructing a Cycle from a dataframe.
  • Partition out calibration/validation data by specifying a tuple of regex patterns that correspond to cycle names. See where cal_cyc_patterns is defined for an example. Typically, it's good to reserve about 25-33% of your data for validation.
  • To set parameters and corresponding ranges that the optimizer is allowed to use in getting the model to match test data, see where params_and_bounds is defined below.

How to Update This Markdown Book

mdBook Documentation

Setup

If not already done, install mdbook

Serving locally

Run the following in the repository root directory:

  1. If any python files were modified,
    1. Install pipx
    2. Install pydoc-markdown
    3. run pydoc-markdown -I python/ --render-toc > docs/src/python-doc.md. Do not modify this file manually.
  2. Run mdbook serve --open docs/

Publishing

  1. Update book.toml or files in docs/src/
  2. Make sure the docs look good locally by running the steps in Serving Locally.
  3. Commit files and push to fastsim-2 branch

After that, a GitHub action will build the book and publish it.

Release Notes

2.1.2 -- SerdeAPI revamp with many new functions, various new vehicles, calibration demo, better error propagation, demo testing 2.1.1 -- license changed to Apache 2.0, default cycle grade and road type to zero if not provided, defaults to regenerative braking parameters, optional documentation fields now generated in Rust 2.1.0 -- release and installation improvements, RustVehicle init cleanup, calibration improvements 2.0.11 - 2.0.22 -- PyPI fixes. Also, Rust version is now >100x faster than Python version. 2.0.10 -- logging fixes, proc macro reorganization, some CAVs performance fixes
2.0.9 -- support for mac ARM/RISC architecture
2.0.8 -- performance improvements
2.0.6 -- dist_v2_m fixes and preliminary CAV functionality
2.0.5 -- added to_rust method for cycle
2.0.4 -- exposed veh.set_veh_mass
2.0.3 -- exposed veh.__post_init__
2.0.2 -- provisioned for non-default vehdb path
2.0.1 -- bug fix
2.0.0 -- All second-by-second calculations are now implemented in both rust and python. Rust provides a ~30x speedup
1.3.1 -- fastsim.simdrive.copy_sim_drive function can deepcopy jit to non-jit (and back) for pickling
1.2.6 -- time dilation bug fix for zero speed
1.2.4 -- bug fix changing == to =
1.2.3 -- veh_file can be passed as standalone argument. fcEffType can be anything if fcEffMap is provided, but typing is otherwise enforced.
1.2.2 -- added checks for some conflicting vehicle parameters. Vehicle parameters fcEffType and vehPtType must now be str type.
1.2.1 -- improved time dilation and added test for it
1.1.7 -- get_numba_veh() and get_numba_cyc() can now be called from already jitted objects
1.1.6 -- another bug fix for numba compatibility with corresponding unit test
1.1.5 -- bug fix for numba compatibility of fcPeakEffOverride and mcPeakEffOverride
1.1.4 -- nan bug fix for fcPeakEffOverride and mcPeakEffOverride
1.1.3 -- provisioned for optional load time motor and engine peak overrides
1.1.2 -- made vehicle loading more more robust
1.1.1 -- made vehicle loading more robust
1.1.0 -- separated jitclasses into own module, made vehicle engine and motor efficiency setting more robust
1.0.4 -- bug fix with custom engine curve
1.0.3 -- bug fixes, faster testing
1.0.2 -- forced type np.float64 on vehicle mass attributes
1.0.1 -- Added vehYear attribute to vehicle and other minor changes. 1.0.0 -- Implemented unittest package. Fixed energy audit calculations to be based on achieved speed. Updated this file. Improved documentation. Vehicle can be instantiated as dict. 0.1.5 -- Updated to be compatible with ADOPT 0.1.4 -- Bug fix: mcEffMap is now robust to having zero as first element 0.1.3 -- Bug fix: fastsim.vehicle.Vehicle method set_init_calcs no longer overrides fcEffMap. 0.1.2 -- Fixes os-dependency of xlwings by not running stuff that needs xlwings. Improvements in functional test. Refinment utomated typying of jitclass objects. 0.1.1 -- Now includes label fuel economy and/or battery kW-hr/mi values that match excel and test for benchmarking against Excel values and CPU time.