Skip to content

Commit

Permalink
Merge pull request #2781 from abillscmu/energy-summary
Browse files Browse the repository at this point in the history
Add theoretical energy to summary variables
  • Loading branch information
valentinsulzer authored Mar 17, 2023
2 parents 5465052 + cbd3565 commit 7ff45ec
Show file tree
Hide file tree
Showing 3 changed files with 59 additions and 12 deletions.
2 changes: 1 addition & 1 deletion CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -6,6 +6,7 @@
- Added "Negative electrode surface potential difference at separator interface [V]", which is the value of the surface potential difference (`phi_s - phi_e`) at the anode/separator interface, commonly controlled in fast-charging algorithms to avoid plating. Also added "Positive electrode surface potential difference at separator interface [V]". ([#2740](https://github.com/pybamm-team/PyBaMM/pull/2740))
- Added "Open-circuit voltage [V]", which is the open-circuit voltage as calculated from the bulk particle concentrations. The old variable "Measured open circuit voltage [V]", which referred to the open-circuit potential as calculated from the surface particle concentrations, has been renamed to "Surface open-circuit voltage [V]". ([#2740](https://github.com/pybamm-team/PyBaMM/pull/2740))
- Added an example for `plot_voltage_components`, explaining what the different voltage components are. ([#2740](https://github.com/pybamm-team/PyBaMM/pull/2740))
- Added method to calculate maximum theoretical energy. ([#2777](https://github.com/pybamm-team/PyBaMM/pull/2777)) and add to summary variables ([#2781](https://github.com/pybamm-team/PyBaMM/pull/2781))

## Bug fixes

Expand Down Expand Up @@ -33,7 +34,6 @@
- Added an option for using a banded jacobian and sundials banded solvers for the IDAKLU solve ([#2677](https://github.com/pybamm-team/PyBaMM/pull/2677))
- The "particle size" option can now be a tuple to allow different behaviour in each electrode ([#2672](https://github.com/pybamm-team/PyBaMM/pull/2672)).
- Added temperature control to experiment class. ([#2518](https://github.com/pybamm-team/PyBaMM/pull/2518))
- Added method to calculate maximum theoretical energy. ([#2777](https://github.com/pybamm-team/PyBaMM/pull/2777))

## Bug fixes

Expand Down
56 changes: 46 additions & 10 deletions pybamm/models/full_battery_models/lithium_ion/electrode_soh.py
Original file line number Diff line number Diff line change
Expand Up @@ -244,6 +244,16 @@ def solve(self, inputs):
raise split_error

sol_dict = {key: sol[key].data[0] for key in sol.all_models[0].variables.keys()}

# Calculate theoretical energy
x_0 = sol_dict["x_0"]
y_0 = sol_dict["y_0"]
x_100 = sol_dict["x_100"]
y_100 = sol_dict["y_100"]
energy = pybamm.lithium_ion.electrode_soh.theoretical_energy_integral(
self.parameter_values, x_100, x_0, y_100, y_0
)
sol_dict.update({"Maximum theoretical energy [W.h]": energy})
return sol_dict

def _set_up_solve(self, inputs):
Expand Down Expand Up @@ -560,9 +570,7 @@ def get_min_max_stoichiometries(
return esoh_solver.get_min_max_stoichiometries()


def calculate_theoretical_energy(
parameter_values, initial_soc=1.0, final_soc=0.0, points=100
):
def theoretical_energy_integral(parameter_values, n_i, n_f, p_i, p_f, points=100):
"""
Calculate maximum energy possible from a cell given OCV, initial soc, and final soc
given voltage limits, open-circuit potentials, etc defined by parameter_values
Expand All @@ -571,10 +579,9 @@ def calculate_theoretical_energy(
----------
parameter_values : :class:`pybamm.ParameterValues`
The parameter values class that will be used for the simulation.
initial_soc : float
The soc at begining of discharge, default 1.0
final_soc : float
The soc at end of discharge, default 1.0
n_i, n_f, p_i, p_f : float
initial and final stoichiometries for the positive and negative
electrodes, respectively
points : int
The number of points at which to calculate voltage.
Expand All @@ -583,9 +590,6 @@ def calculate_theoretical_energy(
E
The total energy of the cell in Wh
"""
# Get initial and final stoichiometric values.
n_i, p_i = get_initial_stoichiometries(initial_soc, parameter_values)
n_f, p_f = get_initial_stoichiometries(final_soc, parameter_values)
n_vals = np.linspace(n_i, n_f, num=points)
p_vals = np.linspace(p_i, p_f, num=points)
# Calculate OCV at each stoichiometry
Expand All @@ -602,3 +606,35 @@ def calculate_theoretical_energy(
# Integrate and convert to W-h
E = np.trapz(Vs, dx=dQ)
return E


def calculate_theoretical_energy(
parameter_values, initial_soc=1.0, final_soc=0.0, points=100
):
"""
Calculate maximum energy possible from a cell given OCV, initial soc, and final soc
given voltage limits, open-circuit potentials, etc defined by parameter_values
Parameters
----------
parameter_values : :class:`pybamm.ParameterValues`
The parameter values class that will be used for the simulation.
initial_soc : float
The soc at begining of discharge, default 1.0
final_soc : float
The soc at end of discharge, default 0.0
points : int
The number of points at which to calculate voltage.
Returns
-------
E
The total energy of the cell in Wh
"""
# Get initial and final stoichiometric values.
x_100, y_100 = get_initial_stoichiometries(initial_soc, parameter_values)
x_0, y_0 = get_initial_stoichiometries(final_soc, parameter_values)
E = theoretical_energy_integral(
parameter_values, x_100, x_0, y_100, y_0, points=points
)
return E
Original file line number Diff line number Diff line change
Expand Up @@ -31,7 +31,18 @@ def test_known_solution(self):
ics = esoh_solver._set_up_solve(inputs)
sol_split = esoh_solver._solve_split(inputs, ics)
for key in sol:
self.assertAlmostEqual(sol[key], sol_split[key].data[0], places=5)
if key != "Maximum theoretical energy [W.h]":
self.assertAlmostEqual(sol[key], sol_split[key].data[0], places=5)
else:
# theoretical_energy is not present in sol_split
x_0 = sol_split["x_0"].data[0]
y_0 = sol_split["y_0"].data[0]
x_100 = sol_split["x_100"].data[0]
y_100 = sol_split["y_100"].data[0]
energy = pybamm.lithium_ion.electrode_soh.theoretical_energy_integral(
parameter_values, x_100, x_0, y_100, y_0
)
self.assertAlmostEqual(sol[key], energy, places=5)

# should still work with old inputs
n_Li = parameter_values.evaluate(param.n_Li_particles_init)
Expand Down

0 comments on commit 7ff45ec

Please sign in to comment.