PyBaMM icon indicating copy to clipboard operation
PyBaMM copied to clipboard

[Bug]: input parameters that affect the initial condition not handled

Open martinjrobins opened this issue 4 months ago • 1 comments

PyBaMM Version

develop

Python Version

3.10

Describe the bug

If an input parameter is used in the initial conditions of the model, then passing in a list of input parameter sets doesn't calculate the correct initial conditions for each set (only the first set is used)

Steps to Reproduce

  1. setup a model with an input parameter used in the initial condition
  2. solve it with multiple input params and check the solution, the initial conditions will be identical for each

Relevant log output


martinjrobins avatar Aug 11 '25 09:08 martinjrobins

This is an inconsistent bug; a model being solved with a single input parameter used in the input params will raise an expected SolverError(Input parameters cannot appear in expression for initial conditions.), while a model with multiple input parameters (one of which is in the initial conditions) will bypass the error and only use the first value for the param in the initial conditions, while correctly using the values for the input parameter not in the initial conditions.

def exception_not_triggered():

    y = pybamm.Variable("y")
    y0 = pybamm.InputParameter("y0")
    k = pybamm.InputParameter("k")

    model = pybamm.BaseModel()
    model.rhs = {y: -k * y}
    model.initial_conditions = {y: y0}
    model.variables = {"y": y}

    disc = pybamm.Discretisation()
    disc.process_model(model)

    t_eval = np.linspace(0.0, 1.0, 6)

    # Three different ICs so each run is clearly distinct
    inputs_list = [
        {"y0": 1.0, "k": 0.5},
        {"y0": 2.0, "k": 1.0},
        {"y0": 3.0, "k": 1.5},
    ]

    print("\n(A) Multiple variables in the input list")
    solver = pybamm.IDAKLUSolver()
    sols = solver.solve(model, t_eval=t_eval, inputs=inputs_list)

    # Extract y(0) actually used per run
    ic_used = [float(sol["y"].entries[0]) for sol in sols]
    print("y(0) per run (expected [1.0, 2.0, 3.0]):", ic_used)
def exception_triggered():

    u0 = pybamm.InputParameter("u0")
    model = pybamm.BaseModel()
    u = pybamm.Variable("u")
    model.rhs = {u: -1 * u}

    model.initial_conditions = {u: u0}

    disc = pybamm.Discretisation()
    disc.process_model(model)

    solver = pybamm.IDAKLUSolver()

    t_eval = np.linspace(0.0, 1.0, 6)

    print("\n(B) Single variable in the input list")

    sols = solver.solve(model, t_eval, inputs=[{"u0": 1}, {"u0": 2}, {"u0": 3}])

    # But putting in a single value for an input parameter works fine:
    # sols = [solver.solve(model, t_eval, inputs={"u0": 1})]

    # Extract u(0) actually used per run
    ic_used = [float(sol["u"].entries[0]) for sol in sols]
    print("u(0) per run (expected [1.0, 2.0, 3.0]):", ic_used)

pipliggins avatar Sep 13 '25 00:09 pipliggins