A simplified example for DiffEqFlux

I am bit new to NeuralODE and hence trying to workout simple examples of own to understand it better.
All Examples on DiffEqFlux webpage are equations where the Neural networks depend on u, or p. What about differential equations which are function of parameter t?

Example: I just tried simple equations –

\frac{df}{dt} = sin(2\pi t/10)

f(0) = -1.0
t = 0:10

Below is my attempt, which is modified version of (https://diffeqflux.sciml.ai/dev/examples/neural_ode_sciml/)

using DifferentialEquations
using DiffEqFlux
using Plots
using GalacticOptim

u0 = -1.0

tspan = (0.0, 10.0)
tsteps = 0.0:0.1:10.0

function sin_diff(u, p, t)
    r = sin(2*pi/10 * t)
    return r'
end

# test the diff eq
prob = ODEProblem(sin_diff, u0, tspan)
sol = solve(prob, Tsit5())
plot(sol)

# set Neural ode
ode_data = Array(solve(prob, Tsit5(), saveat = tsteps))

dudt2 = FastChain(FastDense(1, 50, tanh),
                  FastDense(50, 50, tanh), 
                  FastDense(50, 1))

prob_neuralode = NeuralODE(dudt2, tspan, Tsit5(), saveat = tsteps)

function predict_neuralode(p)
  Array(prob_neuralode(u0, [p]))
end

function loss_neuralode(p)
    pred = predict_neuralode([p])
    loss = sum(abs2, ode_data .- pred) # Just sum of squared error
    return loss, pred
end

callback = function (p, l, pred; doplot = true)
  display(l)
  return false
end

result_neuralode = DiffEqFlux.sciml_train(loss_neuralode, prob_neuralode.p, cb = callback)

i keep getting following error:

ERROR: BoundsError: attempt to access 1-element Vector{Vector{Vector{Float32}}} at index [1:100]

Any gentle nudge in right direction is appreciated. :slight_smile:

Always check your loss function before trying to train. If you ran your loss function, you would’ve seen that it was throwing the same error and thus it has nothing to do with the training setup. So what was wrong with the loss function? As it says, Vector{Vector{...} 1-element… predict_neuralode([p]) you kept wrapping your p in vectors, it was just a one element vector. So just get rid of that, fix your initial condition, and you’re good:

using DifferentialEquations
using DiffEqFlux
using Plots
using GalacticOptim

u0 = -1.0
tspan = (0.0, 10.0)
tsteps = 0.0:0.1:10.0

function sin_diff(u, p, t)
    r = sin(2*pi/10 * t)
    return r'
end

# test the diff eq
prob = ODEProblem(sin_diff, u0, tspan)
sol = solve(prob, Tsit5())
plot(sol)

# set Neural ode
ode_data = Array(solve(prob, Tsit5(), saveat = tsteps))

u0 = [-1.0]
dudt2 = FastChain(FastDense(1, 50, tanh),
                  FastDense(50, 50, tanh),
                  FastDense(50, 1))

prob_neuralode = NeuralODE(dudt2, tspan, Tsit5(), saveat = tsteps)

function predict_neuralode(p)
  Array(prob_neuralode(u0, p))
end

function loss_neuralode(p)
    pred = predict_neuralode(p)
    loss = sum(abs2, ode_data .- pred) # Just sum of squared error
    return loss, pred
end

callback = function (p, l, pred; doplot = true)
  display(l)
  return false
end
loss_neuralode(prob_neuralode.p)

result_neuralode = DiffEqFlux.sciml_train(loss_neuralode, prob_neuralode.p, cb = callback)
1 Like