Skip to content

Commit

Permalink
docs: create pybamm integration example
Browse files Browse the repository at this point in the history
  • Loading branch information
tomjholland committed Jan 11, 2025
1 parent 3a2ca00 commit 7ad73e3
Show file tree
Hide file tree
Showing 3 changed files with 182 additions and 0 deletions.
168 changes: 168 additions & 0 deletions docs/source/examples/working-with-pybamm-models.ipynb
Original file line number Diff line number Diff line change
@@ -0,0 +1,168 @@
{
"cells": [
{
"cell_type": "markdown",
"metadata": {},
"source": [
"# Working with PyBaMM Models"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"PyProBE has bidirectional integration with the popular open-source battery modelling software PyBaMM. This means:\n",
"- PyBaMM simulations can be run from experiment details provided in the README file\n",
"- PyBaMM solutions can be read by PyProBE and displayed alongside experimental data\n",
"\n",
"This example will demonstrate both of these features. We will start by loading some experimental data for the LG M50 cell, which is well paramterised in the literature [1] and has a large associated degradation dataset [2]."
]
},
{
"cell_type": "code",
"execution_count": null,
"metadata": {},
"outputs": [],
"source": [
"import pyprobe\n",
"import pybamm\n",
"import matplotlib.pyplot as plt\n",
"\n",
"cell = pyprobe.Cell(info={\"Model\": \"LG M50\"})\n",
"\n",
"data_directory = \"../../../tests/sample_data/LGM50\"\n",
"\n",
"cell.add_procedure(\n",
" procedure_name=\"BoL RPT\",\n",
" folder_path=data_directory,\n",
" filename=\"NDK - LG M50 deg - exp 2,2 - rig 3 - 25degC - cell C - BoL - RPT0_short_CA4.parquet\",\n",
")"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"Alongside this procedure is a README.yaml file:"
]
},
{
"cell_type": "code",
"execution_count": null,
"metadata": {},
"outputs": [],
"source": [
"with open(data_directory + \"/README.yaml\", \"r\") as file:\n",
" readme = file.read()\n",
" print(readme)"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"The step descriptions in the readme file are PyBaMM experiment strings. PyProBE `RawData` objects include a `pybamm_experiment` property that parses the README into a format that can be passed to a `pybamm.Experiment` constructor:"
]
},
{
"cell_type": "code",
"execution_count": null,
"metadata": {},
"outputs": [],
"source": [
"experiment = pybamm.Experiment(\n",
" cell.procedure[\"BoL RPT\"].pybamm_experiment,\n",
" temperature=298.15,\n",
")\n",
"var_pts = {\n",
" \"x_n\": 20, # negative electrode\n",
" \"x_s\": 5, # separator\n",
" \"x_p\": 20, # positive electrode\n",
" \"r_n\": 100, # negative particle\n",
" \"r_p\": 20, # positive particle\n",
"}\n",
"model = pybamm.lithium_ion.DFN()\n",
"parameters = pybamm.ParameterValues(\"ORegan2022\")\n",
"sim = pybamm.Simulation(\n",
" model, experiment=experiment, parameter_values=parameters, var_pts=var_pts\n",
")\n",
"solution = sim.solve(initial_soc=0.35)\n",
"solution.plot()"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"Having solved the solution, we can import it back into PyProBE to display the model solution alongside the experimental data:"
]
},
{
"cell_type": "code",
"execution_count": null,
"metadata": {},
"outputs": [],
"source": [
"cell.import_pybamm_solution(\"BoL RPT DFN\", [\"BoL RPT\"], solution)\n",
"\n",
"fig, ax = plt.subplots()\n",
"cell.procedure[\"BoL RPT\"].plot(\"Time [s]\", \"Voltage [V]\", ax=ax, label=\"Experiment\")\n",
"cell.procedure[\"BoL RPT DFN\"].plot(\"Time [s]\", \"Voltage [V]\", ax=ax, label=\"Simulation\")"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"The `pybamm_experiment` property can be called on any filtered section of the data in PyProBE:"
]
},
{
"cell_type": "code",
"execution_count": null,
"metadata": {},
"outputs": [],
"source": [
"discharge_experiment = pybamm.Experiment(\n",
" cell.procedure[\"BoL RPT\"].discharge(0).pybamm_experiment,\n",
" temperature=298.15,\n",
")\n",
"sim = pybamm.Simulation(\n",
" model, experiment=discharge_experiment, parameter_values=parameters, var_pts=var_pts\n",
")\n",
"solution = sim.solve()\n",
"\n",
"cell.import_pybamm_solution(\"BoL RPT DFN\", [\"Discharge only\"], solution)\n",
"\n",
"fig, ax = plt.subplots()\n",
"cell.procedure[\"BoL RPT\"].discharge(0).plot(\n",
" \"Step Time [s]\", \"Voltage [V]\", ax=ax, label=\"Experiment\"\n",
")\n",
"cell.procedure[\"BoL RPT DFN\"].discharge(0).plot(\n",
" \"Step Time [s]\", \"Voltage [V]\", ax=ax, label=\"Simulation\"\n",
")"
]
}
],
"metadata": {
"kernelspec": {
"display_name": "pyprobe-dev",
"language": "python",
"name": "pyprobe-dev"
},
"language_info": {
"codemirror_mode": {
"name": "ipython",
"version": 3
},
"file_extension": ".py",
"mimetype": "text/x-python",
"name": "python",
"nbconvert_exporter": "python",
"pygments_lexer": "ipython3",
"version": "3.12.6"
}
},
"nbformat": 4,
"nbformat_minor": 2
}
Binary file not shown.
14 changes: 14 additions & 0 deletions tests/sample_data/LGM50/README.yaml
Original file line number Diff line number Diff line change
@@ -0,0 +1,14 @@
Initial Charge:
Steps:
0: Rest for 2 minutes
1: Charge at 1.5 A until 4.2 V
2: Hold at 4.2 V until 0.05 A
3: Rest for 2 hours
pOCV:
Steps:
4: Rest for 30 seconds
5: Discharge at 0.5 A until 2.5 V
6: Rest for 6 hours
7: Rest for 30 seconds
8: Charge at 0.5 A until 4.2 V
9: Rest for 10 minutes

0 comments on commit 7ad73e3

Please sign in to comment.