Skip to content

Commit 7b9bd2e

Browse files
don't run perturbation
1 parent fca7213 commit 7b9bd2e

File tree

1 file changed

+17
-17
lines changed

1 file changed

+17
-17
lines changed

docs/src/examples/perturbation.md

Lines changed: 17 additions & 17 deletions
Original file line numberDiff line numberDiff line change
@@ -4,7 +4,7 @@
44

55
In the previous tutorial, [Mixed Symbolic-Numeric Perturbation Theory](https://symbolics.juliasymbolics.org/stable/examples/perturbation), we discussed how to solve algebraic equations using **Symbolics.jl**. Here, our goal is to extend the method to differential equations. First, we import the following helper functions that were introduced in [Mixed Symbolic/Numerical Methods for Perturbation Theory - Algebraic Equations](@ref perturb_alg):
66

7-
```@example perturb
7+
```julia
88
using Symbolics, SymbolicUtils
99

1010
def_taylor(x, ps) = sum([a*x^i for (i,a) in enumerate(ps)])
@@ -44,60 +44,60 @@ As the first ODE example, we have chosen a simple and well-behaved problem, whic
4444

4545
with the initial conditions $x(0) = 0$, and $\dot{x}(0) = 1$. Note that for $\epsilon = 0$, this equation transforms back to the standard one. Let's start with defining the variables
4646

47-
```@example perturb
47+
```julia
4848
n = 3
4949
@variables ϵ t y[1:n](t) ∂∂y[1:n](t)
5050
```
5151

5252
Next, we define $x$.
5353

54-
```@example perturb
54+
```julia
5555
x = def_taylor(ϵ, y[3:end], y[2])
5656
```
5757

5858
We need the second derivative of `x`. It may seem that we can do this using `Differential(t)`; however, this operation needs to wait for a few steps because we need to manipulate the differentials as separate variables. Instead, we define dummy variables `∂∂y` as the placeholder for the second derivatives and define
5959

60-
```@example perturb
60+
```julia
6161
∂∂x = def_taylor(ϵ, ∂∂y[3:end], ∂∂y[2])
6262
```
6363

6464
as the second derivative of `x`. After rearrangement, our governing equation is $\ddot{x}(t)(1 + \epsilon x(t))^{-2} + 1 = 0$, or
6565

66-
```@example perturb
66+
```julia
6767
eq = ∂∂x * (1 + ϵ*x)^2 + 1
6868
```
6969

7070
The next two steps are the same as the ones for algebraic equations (note that we pass `1:n` to `collect_powers` because the zeroth order term is needed here)
7171

72-
```@example perturb
72+
```julia
7373
eqs = collect_powers(eq, ϵ, 1:n)
7474
```
7575

7676
and,
7777

78-
```@example perturb
78+
```julia
7979
vals = solve_coef(eqs, ∂∂y)
8080
```
8181

8282
Our system of ODEs is forming. Now is the time to convert `∂∂`s to the correct **Symbolics.jl** form by substitution:
8383

84-
```@example perturb
84+
```julia
8585
D = Differential(t)
8686
subs = Dict(∂∂y[i] => D(D(y[i])) for i in eachindex(y))
8787
eqs = [substitute(first(v), subs) ~ substitute(last(v), subs) for v in vals]
8888
```
8989

9090
We are nearly there! From this point on, the rest is standard ODE solving procedures. Potentially we can use a symbolic ODE solver to find a closed form solution to this problem. However, **Symbolics.jl** currently does not support this functionality. Instead, we solve the problem numerically. We form an `ODESystem`, lower the order (convert second derivatives to first), generate an `ODEProblem` (after passing the correct initial conditions), and, finally, solve it.
9191

92-
```@example perturb
92+
```julia
9393
using ModelingToolkit, DifferentialEquations
9494

9595
@named sys = ODESystem(eqs, t)
9696
sys = structural_simplify(sys)
9797
states(sys)
9898
```
9999

100-
```@example perturb
100+
```julia
101101
# the initial conditions
102102
# everything is zero except the initial velocity
103103
u0 = zeros(2n+2)
@@ -109,13 +109,13 @@ sol = solve(prob; dtmax=0.01)
109109

110110
Finally, we calculate the solution to the problem as a function of `ϵ` by substituting the solution to the ODE system back into the defining equation for `x`. Note that `𝜀` is a number, compared to `ϵ`, which is a symbolic variable.
111111

112-
```@example perturb
112+
```julia
113113
X = 𝜀 -> sum([𝜀^(i-1) * sol[y[i]] for i in eachindex(y)])
114114
```
115115

116116
Using `X`, we can plot the trajectory for a range of $𝜀$s.
117117

118-
```@example perturb
118+
```julia
119119
using Plots
120120

121121
plot(sol.t, hcat([X(𝜀) for 𝜀 = 0.0:0.1:0.5]...))
@@ -129,7 +129,7 @@ For the next example, we have chosen a simple example from a very important clas
129129

130130
The goal is to solve $\ddot{x} + 2\epsilon\dot{x} + x = 0$, where the dot signifies time-derivatives and the initial conditions are $x(0) = 0$ and $\dot{x}(0) = 1$. If $\epsilon = 0$, the problem reduces to the simple linear harmonic oscillator with the exact solution $x(t) = \sin(t)$. We follow the same steps as the previous example.
131131

132-
```@example perturb
132+
```julia
133133
n = 3
134134
@variables ϵ t y[1:n](t) ∂y[1:n] ∂∂y[1:n]
135135
x = def_taylor(ϵ, y[3:end], y[2])
@@ -139,15 +139,15 @@ x = def_taylor(ϵ, y[3:end], y[2])
139139

140140
This time we also need the first derivative terms. Continuing,
141141

142-
```@example perturb
142+
```julia
143143
eq = ∂∂x + 2*ϵ*∂x + x
144144
eqs = collect_powers(eq, ϵ, 0:n)
145145
vals = solve_coef(eqs, ∂∂y)
146146
```
147147

148148
Next, we need to replace ``s and `∂∂`s with their **Symbolics.jl** counterparts:
149149

150-
```@example perturb
150+
```julia
151151
D = Differential(t)
152152
subs1 = Dict(∂y[i] => D(y[i]) for i in eachindex(y))
153153
subs2 = Dict(∂∂y[i] => D(D(y[i])) for i in eachindex(y))
@@ -157,12 +157,12 @@ eqs = [substitute(first(v), subs) ~ substitute(last(v), subs) for v in vals]
157157

158158
We continue with converting 'eqs' to an `ODEProblem`, solving it, and finally plot the results against the exact solution to the original problem, which is $x(t, \epsilon) = (1 - \epsilon)^{-1/2} e^{-\epsilon t} \sin((1- \epsilon^2)^{1/2}t)$,
159159

160-
```@example perturb
160+
```julia
161161
@named sys = ODESystem(eqs, t)
162162
sys = structural_simplify(sys)
163163
```
164164

165-
```@example perturb
165+
```julia
166166
# the initial conditions
167167
u0 = zeros(2n+2)
168168
u0[3] = 1.0 # y₀ˍt

0 commit comments

Comments
 (0)