Repository: pybamm-team/PyBaMM

Issue:
eSOH calculation fails with drive cycle
- PyBaMM version - `$ python -m pip show pybamm`: 21.11
- Python version - `$ python --version`: 3.7

**Describe the bug**
A clear and concise description of what the bug is.

**To Reproduce**
Steps to reproduce the behaviour:
1. Go to the [change input current notebook](https://github.com/pybamm-team/PyBaMM/blob/develop/examples/notebooks/parameterization/change-input-current.ipynb)
2. In cell [5] add an `initial_soc`: e.g. `simulation.solve(initial_soc=0.5)`
4. See error (copied below)

**Additional context**
Tino's comment on it: It looks like it’s trying to solve the eSOH simulation (an algebraic model) with `t_eval=[0]` but since the current in the parameter set is a drive cycle it goes into the drive cycle branch where it expects `t_eval` to match the drive cycle. We should make it not go into that branch if `t_eval=[0]` is provided (which the user would probably not do accidentally)

**Error**
```
---------------------------------------------------------------------------
ValueError                                Traceback (most recent call last)
/tmp/ipykernel_4616/1614736939.py in <module>
      1 # simulate US06 drive cycle (duration 600 seconds)
----> 2 simulation.solve(initial_soc=0.5)
      3 
      4 # plot
      5 simulation.plot()

~/PyBaMM/pybamm/simulation.py in solve(self, t_eval, solver, check_model, save_at_cycles, calc_esoh, starting_solution, initial_soc, **kwargs)
    706             c_p_max = self.parameter_values.evaluate(param.c_p_max)
    707             x, y = pybamm.lithium_ion.get_initial_stoichiometries(
--> 708                 initial_soc, self.parameter_values
    709             )
    710             self.parameter_values.update(

~/PyBaMM/pybamm/models/full_battery_models/lithium_ion/electrode_soh.py in get_initial_stoichiometries(initial_soc, parameter_values)
    136             "C_n": C_n,
    137             "C_p": C_p,
--> 138             "n_Li": n_Li,
    139         },
    140     )

~/PyBaMM/pybamm/simulation.py in solve(self, t_eval, solver, check_model, save_at_cycles, calc_esoh, starting_solution, initial_soc, **kwargs)
    783                     )
    784                     dt_data_min = np.min(np.diff(time_data))
--> 785                     dt_eval_max = np.max(np.diff(t_eval))
    786                     if dt_eval_max > dt_data_min + sys.float_info.epsilon:
    787                         warnings.warn(

<__array_function__ internals> in amax(*args, **kwargs)

~/PyBaMM/.tox/dev/lib/python3.7/site-packages/numpy/core/fromnumeric.py in amax(a, axis, out, keepdims, initial, where)
   2753     """
   2754     return _wrapreduction(a, np.maximum, 'max', axis, None, out,
-> 2755                           keepdims=keepdims, initial=initial, where=where)
   2756 
   2757 

~/PyBaMM/.tox/dev/lib/python3.7/site-packages/numpy/core/fromnumeric.py in _wrapreduction(obj, ufunc, method, axis, dtype, out, **kwargs)
     84                 return reduction(axis=axis, out=out, **passkwargs)
     85 
---> 86     return ufunc.reduce(obj, axis, dtype, out, **passkwargs)
     87 
     88 

ValueError: zero-size array to reduction operation maximum which has no identity
```

Discussion:

Patch:
diff --git a/CHANGELOG.md b/CHANGELOG.md
index b6bc1ba7f..ca0fb48e7 100644
--- a/CHANGELOG.md
+++ b/CHANGELOG.md
@@ -2,11 +2,12 @@
 
 ## Features
 
+-   Experiments can be set to terminate when a voltage is reached (across all steps) ([#1832](https://github.com/pybamm-team/PyBaMM/pull/1832))
 -   Added cylindrical geometry and finite volume method ([#1824](https://github.com/pybamm-team/PyBaMM/pull/1824))
 
 ## Bug fixes
 
--   Experiments can be set to terminate when a voltage is reached (across all steps) ([#1832](https://github.com/pybamm-team/PyBaMM/pull/1832))
+-   Simulations with drive cycles now support `initial_soc` ([#1842](https://github.com/pybamm-team/PyBaMM/pull/1842))
 -   Fixed bug in expression tree simplification ([#1831](https://github.com/pybamm-team/PyBaMM/pull/1831))
 -   Solid tortuosity is now correctly calculated with Bruggeman coefficient of the respective electrode ([#1773](https://github.com/pybamm-team/PyBaMM/pull/1773))
 
diff --git a/pybamm/simulation.py b/pybamm/simulation.py
index a9a8a374c..90fb70d38 100644
--- a/pybamm/simulation.py
+++ b/pybamm/simulation.py
@@ -740,7 +740,9 @@ class Simulation:
                 raise ValueError(
                     "starting_solution can only be provided if simulating an Experiment"
                 )
-            if self.operating_mode == "without experiment":
+            if self.operating_mode == "without experiment" or isinstance(
+                self.model, pybamm.lithium_ion.ElectrodeSOH
+            ):
                 if t_eval is None:
                     raise pybamm.SolverError(
                         "'t_eval' must be provided if not using an experiment or "


Test patch:
diff --git a/tests/unit/test_simulation.py b/tests/unit/test_simulation.py
index df10bd76f..64213ad73 100644
--- a/tests/unit/test_simulation.py
+++ b/tests/unit/test_simulation.py
@@ -226,6 +226,21 @@ class TestSimulation(unittest.TestCase):
         sim.solve(initial_soc=0.8)
         self.assertEqual(sim._built_initial_soc, 0.8)
 
+        # test with drive cycle
+        drive_cycle = pd.read_csv(
+            os.path.join("pybamm", "input", "drive_cycles", "US06.csv"),
+            comment="#",
+            header=None
+        ).to_numpy()
+        timescale = param.evaluate(model.timescale)
+        current_interpolant = pybamm.Interpolant(
+            drive_cycle[:, 0], drive_cycle[:, 1], timescale * pybamm.t
+        )
+        param["Current function [A]"] = current_interpolant
+        sim = pybamm.Simulation(model, parameter_values=param)
+        sim.solve(initial_soc=0.8)
+        self.assertEqual(sim._built_initial_soc, 0.8)
+
     def test_solve_with_inputs(self):
         model = pybamm.lithium_ion.SPM()
         param = model.default_parameter_values