From d422d84ca0beafbebf56a402f20dd4ae1d20b363 Mon Sep 17 00:00:00 2001 From: martinjrobins Date: Wed, 19 Apr 2023 10:16:48 +0000 Subject: [PATCH 1/4] #2789 add "all" to sensitivities for idaklu solver --- pybamm/solvers/idaklu_solver.py | 6 +++++- tests/unit/test_solvers/test_idaklu_solver.py | 6 ++++++ 2 files changed, 11 insertions(+), 1 deletion(-) diff --git a/pybamm/solvers/idaklu_solver.py b/pybamm/solvers/idaklu_solver.py index 3dc2777674..b6865a1f6c 100644 --- a/pybamm/solvers/idaklu_solver.py +++ b/pybamm/solvers/idaklu_solver.py @@ -532,14 +532,18 @@ def _integrate(self, model, t_eval, inputs_dict=None): y_out = sol.y.reshape((number_of_timesteps, number_of_states)) # return sensitivity solution, we need to flatten yS to - # (#timesteps * #states,) to match format used by Solution + # (#timesteps * #states (where t is changing the quickest),) to match format used by Solution + # note that yS is (n_p, n_t, n_y) if number_of_sensitivity_parameters != 0: yS_out = { name: sol.yS[i].reshape(-1, 1) for i, name in enumerate(sensitivity_names) } + # add "all" stacked sensitivities ((#timesteps * #states,#sens_params)) + yS_out["all"] = np.hstack([yS_out[name] for name in sensitivity_names]) else: yS_out = False + if sol.flag in [0, 2]: # 0 = solved for all t_eval if sol.flag == 0: diff --git a/tests/unit/test_solvers/test_idaklu_solver.py b/tests/unit/test_solvers/test_idaklu_solver.py index d2c4b62a23..5f2e7f2ef0 100644 --- a/tests/unit/test_solvers/test_idaklu_solver.py +++ b/tests/unit/test_solvers/test_idaklu_solver.py @@ -200,6 +200,7 @@ def test_ida_roberts_klu_sensitivities(self): model.rhs = {u: a * v} model.algebraic = {v: 1 - v} model.initial_conditions = {u: 0, v: 1} + model.variables = {"2u": 2 * u} disc = pybamm.Discretisation() disc.process_model(model) @@ -250,6 +251,11 @@ def test_ida_roberts_klu_sensitivities(self): dyda_fd = dyda_fd.transpose().reshape(-1, 1) np.testing.assert_array_almost_equal(dyda_ida, dyda_fd) + + # get the sensitivities for the variable + d2uda = sol["2u"].sensitivities["a"] + np.testing.assert_array_almost_equal(2 * dyda_ida[0:200:2], d2uda) + def test_sensitivities_with_events(self): # this test implements a python version of the ida Roberts From 1e8997c0ce0044cacf2783803565e7d6d9a38a15 Mon Sep 17 00:00:00 2001 From: "pre-commit-ci[bot]" <66853113+pre-commit-ci[bot]@users.noreply.github.com> Date: Wed, 19 Apr 2023 10:19:23 +0000 Subject: [PATCH 2/4] style: pre-commit fixes --- pybamm/solvers/idaklu_solver.py | 4 ++-- tests/unit/test_solvers/test_idaklu_solver.py | 3 +-- 2 files changed, 3 insertions(+), 4 deletions(-) diff --git a/pybamm/solvers/idaklu_solver.py b/pybamm/solvers/idaklu_solver.py index b6865a1f6c..8ef3a1bc25 100644 --- a/pybamm/solvers/idaklu_solver.py +++ b/pybamm/solvers/idaklu_solver.py @@ -533,7 +533,7 @@ def _integrate(self, model, t_eval, inputs_dict=None): # return sensitivity solution, we need to flatten yS to # (#timesteps * #states (where t is changing the quickest),) to match format used by Solution - # note that yS is (n_p, n_t, n_y) + # note that yS is (n_p, n_t, n_y) if number_of_sensitivity_parameters != 0: yS_out = { name: sol.yS[i].reshape(-1, 1) @@ -543,7 +543,7 @@ def _integrate(self, model, t_eval, inputs_dict=None): yS_out["all"] = np.hstack([yS_out[name] for name in sensitivity_names]) else: yS_out = False - + if sol.flag in [0, 2]: # 0 = solved for all t_eval if sol.flag == 0: diff --git a/tests/unit/test_solvers/test_idaklu_solver.py b/tests/unit/test_solvers/test_idaklu_solver.py index 5f2e7f2ef0..60a49ffea2 100644 --- a/tests/unit/test_solvers/test_idaklu_solver.py +++ b/tests/unit/test_solvers/test_idaklu_solver.py @@ -251,11 +251,10 @@ def test_ida_roberts_klu_sensitivities(self): dyda_fd = dyda_fd.transpose().reshape(-1, 1) np.testing.assert_array_almost_equal(dyda_ida, dyda_fd) - + # get the sensitivities for the variable d2uda = sol["2u"].sensitivities["a"] np.testing.assert_array_almost_equal(2 * dyda_ida[0:200:2], d2uda) - def test_sensitivities_with_events(self): # this test implements a python version of the ida Roberts From 7727932df5f8c883ce911afba954972fc7b6fbe9 Mon Sep 17 00:00:00 2001 From: martinjrobins Date: Wed, 19 Apr 2023 10:21:55 +0000 Subject: [PATCH 3/4] #2789 style --- pybamm/solvers/idaklu_solver.py | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/pybamm/solvers/idaklu_solver.py b/pybamm/solvers/idaklu_solver.py index 8ef3a1bc25..40f5acb7a7 100644 --- a/pybamm/solvers/idaklu_solver.py +++ b/pybamm/solvers/idaklu_solver.py @@ -532,7 +532,8 @@ def _integrate(self, model, t_eval, inputs_dict=None): y_out = sol.y.reshape((number_of_timesteps, number_of_states)) # return sensitivity solution, we need to flatten yS to - # (#timesteps * #states (where t is changing the quickest),) to match format used by Solution + # (#timesteps * #states (where t is changing the quickest),) + # to match format used by Solution # note that yS is (n_p, n_t, n_y) if number_of_sensitivity_parameters != 0: yS_out = { From d3391b0c063fe70f49ce64ae2859ee4f3207b2f0 Mon Sep 17 00:00:00 2001 From: martinjrobins Date: Wed, 19 Apr 2023 10:24:21 +0000 Subject: [PATCH 4/4] #2789 changelog --- CHANGELOG.md | 1 + 1 file changed, 1 insertion(+) diff --git a/CHANGELOG.md b/CHANGELOG.md index 99111cfaa2..44f05b3bc7 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -10,6 +10,7 @@ ## Bug fixes - Fixed a bug in the discretisation of initial conditions of a scaled variable ([#2856](https://github.com/pybamm-team/PyBaMM/pull/2856)) +- Fixed keyerror on "all" when getting sensitivities from IDAKLU solver([#2883](https://github.com/pybamm-team/PyBaMM/pull/2883)) # Breaking changes