MethodOfLines.jl icon indicating copy to clipboard operation
MethodOfLines.jl copied to clipboard

Possibility to restart solving a system starting from a solution (ics override)

Open Qfl3x opened this issue 2 years ago • 6 comments

Basically the possibility to do solve(discretized_problem, previous_solution, p = new_parameters, otherkwargs...) by overriding the previous ics (or in some other way).

Qfl3x avatar Sep 11 '23 13:09 Qfl3x

I'd recommend to do this with an interpolation, There is an idea in the works to to do this automatically in some cases but in needs changes in Interpolations.jl

xtalax avatar Sep 11 '23 14:09 xtalax

Any hint how this could be implemented?

Qfl3x avatar Sep 11 '23 15:09 Qfl3x

remake in SciMLBase supports applying new u0's: https://github.com/SciML/SciMLBase.jl/blob/03cdaedfd3af1ece7c897f6d28ad2d4236ead4d9/src/remake.jl#L52

Qfl3x avatar Sep 12 '23 09:09 Qfl3x

Ah ok I have an idea, yes I will implement a helper that will discretize a new u0 on to the grid, or you can use it directly if you have the same discretization

xtalax avatar Sep 12 '23 15:09 xtalax

Perhaps something like this (seems to work):

function resolve(ps, sol)
    ps = # Make a vector of pairs here
    _prob = remake(prob, p=ps, u0=vcat([val[end,:] for val in values(sol.u)]...))
    
    solve(_prob, Tsit5(), saveat=0.1)
end

Qfl3x avatar Sep 18 '23 07:09 Qfl3x

Full MWE (for 2 dependent variables):

using DifferentialEquations, ModelingToolkit, MethodOfLines, DomainSets

# Parameters, variables, and derivatives
@parameters t x
@variables u(..) v(..)
@parameters α β
Dt = Differential(t)
Dxx = Differential(x)^2

# 1D PDE and boundary conditions
eq  = [Dt(u(t, x)) ~ (α + β) * Dxx(u(t, x)),
        Dt(v(t, x)) ~ (α + β) * Dxx(v(t, x))]
bcs = [u(0, x) ~ cos(x),
        u(t, 0) ~ exp(-t),
        u(t, 1) ~ exp(-t) * cos(1),
        v(0,x) ~ sin(x),
        v(t,0) ~ exp(-t),
        v(t,1) ~ 0.,]

# Space and time domains
domains = [t ∈ Interval(0.0, 1.0),
           x ∈ Interval(0.0, 1.0)]

# Parameters
ps = [α => 1.2, β => 2.1]
# PDE system
@named pdesys = PDESystem(eq, bcs, domains, [t, x], [u(t, x), v(t,x)], ps)

# Method of lines discretization
dx = 0.1
order = 2
discretization = MOLFiniteDifference([x => dx], t)

# Convert the PDE problem into an ODE problem
prob = discretize(pdesys,discretization)

function pde_solution(ps)
    ps = [α => ps[1], β => ps[2]]
    _prob = remake(prob, p=ps)
    
    solve(_prob, Tsit5(), saveat=0.1)
end

function resolve(ps, sol)
    ps = [α => ps[1], β => ps[2]]
    _prob = remake(prob, p=ps, u0=vcat([val[end,:] for val in values(sol.u)]...))
    
    solve(_prob, Tsit5(), saveat=0.1)
end

sol = pde_solution([10.,10.]);
sol2 = resolve([-1.,-1.], sol);

all(sol2.prob.u0[1:11] .== sol.u[u(t,x)][end,:])

Qfl3x avatar Sep 18 '23 07:09 Qfl3x