# "Tuple type used as state" error in solve

I am solving a system of two equations two unknowns using `ODEProblem/solve` pair. This works as long as I do not include them within a function. If I do, I get an error:

``````ERROR: Tuple type used as a state. Since a tuple does not have vector
properties, it will not work as a state type in equation solvers.
to static array constructors `SA[]`. For example, change:

```julia
function ftup((a,b),p,t)
return b,-a
end
u0 = (1.0,2.0)
tspan = (0.0,1.0)
ODEProblem(ftup,u0,tspan)
```

to:

```julia
using StaticArrays
function fsa(u,p,t)
SA[u[2],u[1]]
end
u0 = SA[1.0,2.0]
tspan = (0.0,1.0)
ODEProblem(ftup,u0,tspan)
```

This will be safer and fast for small ODEs. For more information, see:
https://diffeq.sciml.ai/stable/tutorials/faster_ode_example/#Further-Optimizations-of-Small-Non-Stiff-ODEs-with-StaticArrays

Stacktrace:
[1] get_concrete_u0(prob::ODEProblem{Tuple{Float32, Float32}, Tuple{Float64, Float64}, true, Vector{Float64}, ODEFunction{true, SciMLBase.AutoSpecialize, typeof(lotka!), UniformScaling{Bool}, Nothing, Nothing, Nothing, Nothing, Nothing, Nothing, Nothing, Nothing, Nothing, Nothing, Nothing, Nothing, Nothing, typeof(SciMLBase.DEFAULT_OBSERVED), Nothing, Nothing}, Base.Pairs{Symbol, Union{}, Tuple{}, NamedTuple{(), Tuple{}}}, SciMLBase.StandardODEProblem}, isadapt::Bool, t0::Float64, kwargs::Base.Pairs{Symbol, Any, NTuple{5, Symbol}, NamedTuple{(:u0, :p, :abstol, :reltol, :saveat), Tuple{Tuple{Float32, Float32}, Vector{Float64}, Float64, Float64, Float64}}})
@ DiffEqBase ~/.julia/packages/DiffEqBase/nysQq/src/solve.jl:1050
[2] get_concrete_problem(prob::ODEProblem{Tuple{Float32, Float32}, Tuple{Float64, Float64}, true, Vector{Float64}, ODEFunction{true, SciMLBase.AutoSpecialize, typeof(lotka!), UniformScaling{Bool}, Nothing, Nothing, Nothing, Nothing, Nothing, Nothing, Nothing, Nothing, Nothing, Nothing, Nothing, Nothing, Nothing, typeof(SciMLBase.DEFAULT_OBSERVED), Nothing, Nothing}, Base.Pairs{Symbol, Union{}, Tuple{}, NamedTuple{(), Tuple{}}}, SciMLBase.StandardODEProblem}, isadapt::Bool; kwargs::Base.Pairs{Symbol, Any, NTuple{5, Symbol}, NamedTuple{(:u0, :p, :abstol, :reltol, :saveat), Tuple{Tuple{Float32, Float32}, Vector{Float64}, Float64, Float64, Float64}}})
@ DiffEqBase ~/.julia/packages/DiffEqBase/nysQq/src/solve.jl:915
[3] solve_up(prob::ODEProblem{Tuple{Float32, Float32}, Tuple{Float64, Float64}, true, Vector{Float64}, ODEFunction{true, SciMLBase.AutoSpecialize, typeof(lotka!), UniformScaling{Bool}, Nothing, Nothing, Nothing, Nothing, Nothing, Nothing, Nothing, Nothing, Nothing, Nothing, Nothing, Nothing, Nothing, typeof(SciMLBase.DEFAULT_OBSERVED), Nothing, Nothing}, Base.Pairs{Symbol, Union{}, Tuple{}, NamedTuple{(), Tuple{}}}, SciMLBase.StandardODEProblem}, sensealg::Nothing, u0::Tuple{Float32, Float32}, p::Vector{Float64}, args::Vern7; kwargs::Base.Pairs{Symbol, Float64, Tuple{Symbol, Symbol, Symbol}, NamedTuple{(:abstol, :reltol, :saveat), Tuple{Float64, Float64, Float64}}})
@ DiffEqBase ~/.julia/packages/DiffEqBase/nysQq/src/solve.jl:833
[4] solve(prob::ODEProblem{Tuple{Float32, Float32}, Tuple{Float64, Float64}, true, Vector{Float64}, ODEFunction{true, SciMLBase.AutoSpecialize, typeof(lotka!), UniformScaling{Bool}, Nothing, Nothing, Nothing, Nothing, Nothing, Nothing, Nothing, Nothing, Nothing, Nothing, Nothing, Nothing, Nothing, typeof(SciMLBase.DEFAULT_OBSERVED), Nothing, Nothing}, Base.Pairs{Symbol, Union{}, Tuple{}, NamedTuple{(), Tuple{}}}, SciMLBase.StandardODEProblem}, args::Vern7; sensealg::Nothing, u0::Nothing, p::Nothing, wrap::Val{true}, kwargs::Base.Pairs{Symbol, Float64, Tuple{Symbol, Symbol, Symbol}, NamedTuple{(:abstol, :reltol, :saveat), Tuple{Float64, Float64, Float64}}})
@ DiffEqBase ~/.julia/packages/DiffEqBase/nysQq/src/solve.jl:803
[5] generate_solution_data(system_odes::Function, tspan::Vector{Float64}, u0::Tuple{Float32, Float32}, p_::Vector{Float64}; saveat::Float64)
@ Main ~/src/2022/basic_UODE/lotka-voltera/Universal_Differential_Equations_PARTIALLY_WORKING.jl:47
[6] generate_solution_data(system_odes::Function, tspan::Vector{Float64}, u0::Tuple{Float32, Float32}, p_::Vector{Float64})
@ Main ~/src/2022/basic_UODE/lotka-voltera/Universal_Differential_Equations_PARTIALLY_WORKING.jl:44
[7] top-level scope
@ ~/src/2022/basic_UODE/lotka-voltera/Universal_Differential_Equations_PARTIALLY_WORKING.jl:51
``````

Here is my code, abridged

``````function lotka!(du, u, p, t)
α, β, γ, δ = p
du[1] = α*u[1] - β*u[2]*u[1]
du[2] = γ*u[1]*u[2]  - δ*u[2]
return du
end

p_ = p_LV = [1.3, 0.9, 0.8, 1.8]
tspan = (0.0f0,3.0f0)
u0 = [0.44249296,4.6280594]
saveat=0.1

# the next two lines execute without error
prob = ODEProblem(lotka!, u0,tspan, p_)
solution = solve(prob, Vern7(), abstol=1e-12, reltol=1e-12, saveat=0.1)

# invoking this function generates a "Tuple type used as state" error
function generate_solution_data(system_odes, tspan, u0, p_; saveat=0.1)
# Define the experimental parameter
prob = ODEProblem(system_odes, u0,tspan, p_)
solution = solve(prob, Vern7(), abstol=1e-12, reltol=1e-12, saveat=0.1)
return solution
end

# the next line returns the error below.
solution = generate_solution_data(lotka!, u0, tspan, p_LV)
``````

My system is Julia 1.8.3 on a Mac M1 running Ventura. I think that there is something fundamental I am not grokking!

The function is defined as `generate_solution_data(system_odes, tspan, u0` but you call it like `generate_solution_data(lotka!, u0, tspan`. `tspan` and `u0` are flipped.

Wow! Thank you so much. Why such a complex door message? Would an error saying there is a type mismatch be sufficient? The message threw me off.