Skip to content

Commit ec8c255

Browse files
committed
Add dae_order_lowering
1 parent 92f78c9 commit ec8c255

File tree

3 files changed

+58
-2
lines changed

3 files changed

+58
-2
lines changed

src/ModelingToolkit.jl

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -175,7 +175,7 @@ export ControlSystem
175175
export alias_elimination, flatten
176176
export connect, @connector, Connection, Flow, Stream, instream
177177
export isinput, isoutput, getbounds, hasbounds, isdisturbance, istunable, getdist, hasdist, tunable_parameters
178-
export ode_order_lowering, liouville_transform
178+
export ode_order_lowering, dae_order_lowering, liouville_transform
179179
export runge_kutta_discretize
180180
export PDESystem
181181
export Differential, expand_derivatives, @derivatives

src/structural_transformation/bareiss.jl

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -222,7 +222,7 @@ function nullspace(A; col_order=nothing)
222222
@swap(col_order[i],col_order[cp])
223223
end
224224
end
225-
225+
226226
N = ModelingToolkit.reduced_echelon_nullspace(rank, B)
227227
apply_inv_pivot_rows!(N, column_pivots)
228228
end

src/systems/diffeqs/first_order_transform.jl

Lines changed: 56 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -12,6 +12,14 @@ function ode_order_lowering(sys::ODESystem)
1212
return sys
1313
end
1414

15+
function dae_order_lowering(sys::ODESystem)
16+
iv = get_iv(sys)
17+
eqs_lowered, new_vars = dae_order_lowering(equations(sys), iv, states(sys))
18+
@set! sys.eqs = eqs_lowered
19+
@set! sys.states = new_vars
20+
return sys
21+
end
22+
1523
function ode_order_lowering(eqs, iv, states)
1624
var_order = OrderedDict{Any,Int}()
1725
D = Differential(iv)
@@ -47,3 +55,51 @@ function ode_order_lowering(eqs, iv, states)
4755
# we want to order the equations and variables to be `(diff, alge)`
4856
return (vcat(diff_eqs, alge_eqs), vcat(diff_vars, setdiff(states, diff_vars)))
4957
end
58+
59+
function dae_order_lowering(eqs, iv, states)
60+
var_order = OrderedDict{Any,Int}()
61+
D = Differential(iv)
62+
diff_eqs = Equation[]
63+
diff_vars = OrderedSet()
64+
alge_eqs = Equation[]
65+
vars = Set()
66+
subs = Dict()
67+
68+
for (i, eq) enumerate(eqs)
69+
vars!(vars, eq)
70+
n_diffvars = 0
71+
for vv in vars
72+
isdifferential(vv) || continue
73+
var, maxorder = var_from_nested_derivative(vv)
74+
isparameter(var) && continue
75+
n_diffvars += 1
76+
order = get(var_order, var, nothing)
77+
seen = order !== nothing
78+
if !seen
79+
order = 1
80+
end
81+
maxorder > order && (var_order[var] = maxorder)
82+
var′ = lower_varname(var, iv, maxorder - 1)
83+
subs[vv] = D(var′)
84+
if !seen
85+
push!(diff_vars, var′)
86+
end
87+
end
88+
n_diffvars == 0 && push!(alge_eqs, eq)
89+
empty!(vars)
90+
end
91+
92+
for (var, order) var_order
93+
for o in (order-1):-1:1
94+
lvar = lower_varname(var, iv, o-1)
95+
rvar = lower_varname(var, iv, o)
96+
push!(diff_vars, lvar)
97+
98+
rhs = rvar
99+
eq = Differential(iv)(lvar) ~ rhs
100+
push!(diff_eqs, eq)
101+
end
102+
end
103+
104+
return ([diff_eqs; substitute.(eqs, (subs,))], vcat(collect(diff_vars), setdiff(states, diff_vars)))
105+
end

0 commit comments

Comments
 (0)