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

Make PSID differentiable w.r.t. parameters

Open m-bossart opened this issue 11 months ago • 0 comments

Making PSID differentiable w.r.t parameters opens up many capabilities in parameter estimation including the training of data-driven models directly within PSID simulations. While the SciML ecosystem has the capability to backpropagate through ODE solves (SciMLSensitivity), PSID is not currently compatible. The crux of the problem is in how PSID handles parameters, which is different than the assumed handling as a flat vector in the SciML ecosystem required to take advantage of the sensitivity analysis.

Below is pseudo-code of the desired capability for calculating the gradient of the solution w.r.t the inertia in a OMIB system.

using PowerSimulationsDynamics
using PowerSystems
using OrdinaryDiffEq
using SciMLSensitivity
using Zygote

sys = build_system(PSIDTestSystems, "psid_test_omib")
dyngen = get_component(DynamicGenerator, sys, "generator-102-1")
pert = ControlReferenceChange(t_perturb, dyngen, :P_ref, Pref_perturb )
sim = Simulation(MassMatrixModel, sys, pwd(), tspan, pert)
execute!(sim, Rodas5())
res = read_results(sim)
t, δ_true = get_state_series(res, ("generator-102-1", :δ), dt=0.01)

function simulate_with_new_H(H)
     set_H!(get_shaft(dyngen), H)
     sim = Simulation(MassMatrixModel, sys, pwd(), tspan, pert)
     execute!(sim, Rodas5())
     res = read_results(sim)
     t, δ_pred = get_state_series(res, ("generator-102-1", :δ), dt=0.01)
    loss = sum(abs.(δ_true - δ_pred )
end 
gradient((H) -> simulate_with_new_H(H), 2.0)

m-bossart avatar Mar 15 '24 16:03 m-bossart