# Working with a single equation, split up into several

**URL:** <https://discourse.julialang.org/t/working-with-a-single-equation-split-up-into-several/69551>\
**Category:** General Usage\
**Tags:** modelingtoolkit\
**Created:** [October 11, 2021, 9:58am UTC](https://discourse.julialang.org/t/working-with-a-single-equation-split-up-into-several/69551 "2021-10-11T09:58:30Z")\
**Posts on this page:** 2\
**Page:** 1

<div class="post-metadata">

**Author:** ![adomasbaliuka](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/adomasbaliuka/32/29790_2.png) [@adomasbaliuka](https://discourse.julialang.org/u/adomasbaliuka)\
**Post date:** [October 11, 2021, 9:58am UTC](https://discourse.julialang.org/t/working-with-a-single-equation-split-up-into-several/69551/1 "2021-10-11T09:58:30Z")

</div>

I’m trying to get into ModelingToolkit.jl but having some trouble understanding the documentation, which doesn’t seem to include _basic_ examples. Solving nonlinear ODEs and plotting solutions in 3D is very impressive, but at the moment the framework still feels very hard to get into, especially if one doesn’t need differential equations.

Let’s say I have a **single non-linear equation** for a quantity z:

```julia
using ModelingToolkit
using NonlinearSolve

@variables u v w x y z
@parameters a b

eqn = z ~ a * u^2 + b * (v + 2w + 3x + 4y)

```

**Question 1: How can I best plug in numbers for variables and get a number as a result?** (e.g. all parameters and variables except z)

_Note: you might object that ModelingToolkit.jl is not responsible for such trivial things. However, in my opinion, when working with models of any kind, it is essential to be able to do simple things, such as plugging in numbers, plotting equations as functions, etc._

The best solution I came up with after quite a bit of trying seems a bit cumbersome and is not part of ModelingToolkit:

```julia
using Symbolics
substitute(eqn, Dict([u=>1., v=>2., w=>3., x=>4., y=>5., a=>6., b=>7.]))
# Result: `z ~ 286.0`. Still need to extract the number, too.

```

My actual equation is quite long. Publications split it up into several terms and give them names. Some of the terms appear multiple times as sub-expressions of other terms. I would like to be able to present the equations in this form before manipulating them, so readers can verify they are copied from the paper. For example, **the same equation above** could be written as four equations using helper variables h\_1, h\_2,h\_3 as:

```julia
@variables h_1, h_2, h_3

eqns = [
  z ~ h_1 + b * (h_2 + h_3)
h_1 ~ a * u^2
h_2 ~ v + 2w
h_3 ~ 3x + 4y
]

```

**Question 2: How can I get back the single equation by substituting them into one another?** (Or, if that’s not possible, at least verify automatically that the equation above is the same as this system?)

I tried turning the equations into a `NonlinearSystem` and using `structural_simplify`, but it doesn’t work (“ExtraVariablesSystemException: The system is unbalanced…”). The functions (e.g. `simplify` or `solve_for`) in the `Symbolics` package also didn’t work.

Possibly, I could achieve a similar effect by using functions instead of variables or `Equation`s? What is the right way to approach this?

---

<div class="post-metadata">

**Author:** ![adomasbaliuka](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/adomasbaliuka/32/29790_2.png) [@adomasbaliuka](https://discourse.julialang.org/u/adomasbaliuka)\
**Post date:** [January 12, 2022, 1:56pm UTC](https://discourse.julialang.org/t/working-with-a-single-equation-split-up-into-several/69551/2 "2022-01-12T13:56:12Z")

</div>

I kind-of solved the problem with ugly hacks. If anyone is interested, here is my haphazard solution, which just calls `Symbolics.substitute` until all the helper variables are gone.

```julia
using Symbolics

"""
Substitutes expressions of `target_eqn` as specified by equations `source_eqns`.
For each equation in `source_eqns`, substitutes its `lhs` by its `rhs` until none of the `lhs` are left in `target_eqn`.

TODO this is just a crappy prototype!
"""
function substitute_all(target_eqn, source_eqns,)
    all_eqns = [target_eqn, source_eqns...]

    eliminated_symbols = Set(map(x->x.lhs, source_eqns))
    length(eliminated_symbols) == length(source_eqns) || error("Redundant equations!")

    for i in 2:length(all_eqns)
        all_eqns = substitute.(all_eqns, (Dict(all_eqns[i].lhs => all_eqns[i].rhs),))
    end

    return all_eqns[1]
end

# test the function using above example

@variables u v w x y z a b

eqn_to_recover = z ~ a * u^2 + b * (v + 2w + 3x + 4y)

# define split-up version
helper_variables = @variables h_1, h_2, h_3

target_eqn = z ~ h_1 + b * (h_2 + h_3)

source_eqns = [
    h_1 ~ a * u^2
    h_2 ~ v + 2w
    h_3 ~ 3x + 4y
]

substitute_all(target_eqn, source_eqns,) == eqn_to_recover || error("Failure")

```
