@@ -467,23 +467,53 @@ function find_derivatives!(vars, expr, f)
467467 return vars
468468end
469469
470- function collect_vars! (unknowns, parameters, expr, iv; op = Differential)
470+ """
471+ $(TYPEDSIGNATURES)
472+
473+ Search through equations and parameter dependencies of `sys`, where sys is at a depth of
474+ `depth` from the root system, looking for variables scoped to the root system. Also
475+ recursively searches through all subsystems of `sys`, increasing the depth if it is not
476+ `-1`. A depth of `-1` indicates searching for variables with `GlobalScope`.
477+ """
478+ function collect_scoped_vars! (unknowns, parameters, sys, iv; depth = 1 , op = Differential)
479+ for eq in get_eqs (sys)
480+ collect_vars! (unknowns, parameters, eq. lhs, iv; depth, op)
481+ collect_vars! (unknowns, parameters, eq. rhs, iv; depth, op)
482+ end
483+ if has_parameter_dependencies (sys)
484+ for eq in get_parameter_dependencies (sys)
485+ if eq isa Pair
486+ collect_vars! (unknowns, parameters, eq[1 ], iv; depth, op)
487+ collect_vars! (unknowns, parameters, eq[2 ], iv; depth, op)
488+ else
489+ collect_vars! (unknowns, parameters, eq. lhs, iv; depth, op)
490+ collect_vars! (unknowns, parameters, eq. rhs, iv; depth, op)
491+ end
492+ end
493+ end
494+ newdepth = depth == - 1 ? depth : depth + 1
495+ for ssys in get_systems (sys)
496+ collect_scoped_vars! (unknowns, parameters, ssys, iv; depth = newdepth, op)
497+ end
498+ end
499+
500+ function collect_vars! (unknowns, parameters, expr, iv; depth = 0 , op = Differential)
471501 if issym (expr)
472- collect_var! (unknowns, parameters, expr, iv)
502+ collect_var! (unknowns, parameters, expr, iv; depth )
473503 else
474504 for var in vars (expr; op)
475505 if iscall (var) && operation (var) isa Differential
476506 var, _ = var_from_nested_derivative (var)
477507 end
478- collect_var! (unknowns, parameters, var, iv)
508+ collect_var! (unknowns, parameters, var, iv; depth )
479509 end
480510 end
481511 return nothing
482512end
483513
484- function collect_var! (unknowns, parameters, var, iv)
514+ function collect_var! (unknowns, parameters, var, iv; depth = 0 )
485515 isequal (var, iv) && return nothing
486- getmetadata (var, SymScope, LocalScope ()) == LocalScope ( ) || return nothing
516+ check_scope_depth ( getmetadata (var, SymScope, LocalScope ()), depth ) || return nothing
487517 if iscalledparameter (var)
488518 callable = getcalledparameter (var)
489519 push! (parameters, callable)
@@ -500,6 +530,24 @@ function collect_var!(unknowns, parameters, var, iv)
500530 return nothing
501531end
502532
533+ """
534+ $(TYPEDSIGNATURES)
535+
536+ Check if the given `scope` is at a depth of `depth` from the root system. Only
537+ returns `true` for `scope::GlobalScope` if `depth == -1`.
538+ """
539+ function check_scope_depth (scope, depth)
540+ if scope isa LocalScope
541+ return depth == 0
542+ elseif scope isa ParentScope
543+ return depth > 0 && check_scope_depth (scope. parent, depth - 1 )
544+ elseif scope isa DelayParentScope
545+ return depth >= scope. N && check_scope_depth (scope. parent, depth - scope. N)
546+ elseif scope isa GlobalScope
547+ return depth == - 1
548+ end
549+ end
550+
503551"""
504552Find all the symbolic constants of some equations or terms and return them as a vector.
505553"""
0 commit comments