Professional Documents
Culture Documents
Differential Equations in MATLAB
Differential Equations in MATLAB
Cheng Ly1
1
15260, USA.
E-mail: chengly@math.pitt.edu
This workshop assumes you have some familiarity with ordinary (ODEs) and partial
differential equations (PDEs), and also that you are relatively comfortable with basic
programming in Matlab.
Matlab is a very powerful high-level computing tool with a lot of nice built in packages. It is relatively easy to learn, but lags in computation time compared to complied
languages such as Fortran, C, or C++. In particular, when solving PDEs with 3 or more
spatial dimensions (i.e., 4 or more when including time) Matlab is not something you
should use. However, for 2 or less spatial dimensions, Matlab is fast enough these days
to be successfully utilized.
Numerical simulations are undoubtedly an important tool in investigating the complex behavior of many systems (presumably that is why you are here unless you only
came for the free pizza in which case you should...). Mathematical analysis and ingenuity
are obviously important as well, but the value of numerical tools cannot be underscored.
>> x(2:end)
and
>> x(1:end-1)
You can also reverse the order of the entries with a command like
>> x(end:-1:2)
Important functions. The function zeros(n,m) and ones(n,m) creates matrices
of size n x m with all 0s and 1 entries (respectively). Also, eye(N) creates the identity
matrix of size N x N.
You can concatenate vectors and columns easily in between brackets. Type in the
following commands:
>> A=[1 0 -1; 2*ones(3,1); 8 zeros(2,1)]
>> B=[eye(3); A]
You can also multiply and divide component-wise when you have a matrix/vector
with the . operator. Type:
>> x./3
to divide every entry in x by 3.
The function diag(x) creates a square matrix with x on the main diagonal and 0s
on the off diagonal. The matrix of size N x N where N is length of the vector x. The
command length(x) will return this length:
>> length(x)
Type:
>> C=diag(x)
The function diag can also be used to create matrices with entries above or below
the main diagonal. If you want to create an N x N matrix with a vector z that is of size
N-1 x 1, that is one above the main diagonal, you can type:
>> z=[8; 4];
>> diag(z,1)
to create a 3 x 3 matrix. Or if you want z to be 1 below the main diagonal type:
>> diag(z,-1)
For example, can you guess what you would get when you type in
>> D=diag(x) + diag(x(1:2),1) - diag(x(2:3),-1)
Now what we have a better understanding of how vectors/matrices work, we can
proceed. Type
>> clear
2
2. ODEs
Matlab can solve large dimensional ODE systems with built-in solvers. You may want
to consider using XPP if you are going to alter many parameters and do other dynamical
system things (i.e., bifurcation diagrams, phaseplane analysis, etc.). Note that higher
level programming is easier to implement in Matlab. Examples are complicated logical
(if-else) statements in your system, weird boundary conditions, as well as look up
tables [Sorry Bard]. You can use look-up tables in XPP as well, but Im not sure how
well it is documented.
There are various methods (see Matlabs documenation), but I will consider my
favorite stiff solver: ode15s.
For this workshop, we will assume the ODEs are first-order. For higher orders, we
simply have to introduce auxiliary variables and enlarge the size of the system.
Consider y R2 , and an ODE system of the form
y1 = y1 (a1 + a2 y2 )
(1)
y2 = y1 y2
(2)
Open up the file rhs.m ; notice the syntax for this file. It basically specifies the
right-hand side of the ODE system above. The parameters come after t (independent
variable) and y (the functions y1 =y(1) and y2 =y(2).
Fill in the appropriate commands for y1 =dy(1) and y2 =dy(2)..... ask for help if
there is something unclear.
Now open the file slv ode.m. Notice the initial conditions are random. Also the
parameters for the time-length (t end) and a1 and a2 are already filled in (you can play
with these later). Ignore the command options=..; you can explore this later by typing
help ode15s in the command lind. You will write the syntax to solve the ODE
[T,Y] = ode15s(@rhs,[0 t end],y0,options,a 1,a 2);
Type the following in the command line:
>> slv ode
do this several times and see what happens.
Before moving on to the next section, type:
>> clear
3. PDEs
We will discuss how to numerically solve partial differential equations of the form (x R1
and t [0, )):
o
o
u(x, t)
2 n
n
A(x, t)u(x, t) 2 D(x)u(x, t) = 0.
+
t
x
x
(3)
These are called advection-diffusion equations and arise all of the time in the physical
and life sciences. This encompasses equations called Fokker-Planck, Black-Scholes,
and a biological phenomena known as chemotaxis with some augmentations.
For this workshop, we will consider the following advection-diffusion equation:
o
o
2 n
u(x, t) 1 n
((t) x)u(x, t) D 2 u(x, t) = 0
+
t
x
x
(4)
move (or advect) toward (t) with a velocity of 1 . Thus, if is smaller, the mass moves
faster towards (t). Of course, the value (t) is changingnin timeo which adds to the
2
complications of these dynamics. The diffusion term D x
u(x, t) spreads or smears
2
4
out the mass equally in all directions (2 directions here since x R1 ) with a coefficient of
D that is constant here. Think of heat or gas diffusing on a line. Many different systems
have a D that depends on x: D(x) (equation 3), which also complicates things.
3.1. Implementation
Let us first rewrite the PDE
o
u(x, t)
2 u(x, t) (t) u(x, t)
1 n
xu(x, t) + D
=
t
x
x2
(5)
Discretize time with a mesh size t << 1 (say t = 0.01), and label tk = 0 + t(k 1)
(for k = 1, 2, .., 5001). In general, k = 1, 2, ..., Tend/t + 1. We approximate the time-
u
t
for the
t variables, we are assuming equally spaced points (i.e., uniform mesh) 1 , but t 6= x
necessarily (in fact, this is usually the case). Write equation (4) as follows:
o
2 u(x, t) (t) u(x, t)
n
u(x, tk ) u(x, tk1)
xu(x, t) + D
=
t
x
x2
(6)
Let ~u = [u1 ; u2 ; ..; uN ], where uj = u(xj , t). We will now create the matrices to
discretize the right-hand-side of equation (5).
Advection to 0 operator (M0) We want a matrix M0 that represents the
operator:
o
n
xu(x, t) = M0~u
x
We will use a simple forward finite difference method:
o x u x u
n
j+1 j+1
j j
xj u(xj , t) =
x
x
1
Many complicated numerical solvers do not assume a uniform mesh, although you can get quite far
with this assumption. Some people have debated this issue and the answer is that it all depends on
your problem (i.e., domain, stiffness, etc.).
xj+1
; 0; ..0]
x
o
n
u(x, t) = Am~u
x
We will use a simple forward finite difference method:
o u
n
j+1 + uj
u(xj , t) =
x
x
1
1
So the j th row of Am looks like [0...; x
; x
; 0; ..0]
I have avoided talking about boundary conditions so far because they can be quite
complicated. Neglecting boundary conditions, you can now think about how you would
create the matrices. Some people would use a for-loop but they are NOT a good idea
in Matlab because they take enormous computation times (for example if you make N
large). You should look at the diagonal structure of these operators (recall the function
diag).
Now, open the file make matrix.m. Look at the syntax and the commands. If you
have any questions, now is the time to discuss this.
In this file (make matrix.m), insert the following commands in
M0=diag([0;-x(2:end-1);0]./dx)+diag([x(2:end-1);0]./dx,1);
and
Md=diag([-1;-2*ones(N-2,1);-1]./(dx^ 2))+...
diag(ones(N-1,1)./(dx^ 2),1)+diag(ones(N-1,1)./(dx^ 2),-1);
and
Am=diag([0;ones(N-2,1);0]./dx)-diag([ones(N-2,1);0]./dx,1);
After this, type in
M0=sparse(M0);
Md=sparse(Md);
6
Am=sparse(Am);
to make the matrices sparse. This will speed up the matrix-vector solver that we will
write below.
3.1.1. Solve the PDE with Trapezoidal Rule
Now that we have all our operators created in the file make matrix.m, we are ready
to (crudely) solve this system. The trapezoidal rule is a decent implicit solver (recall
equation (5)):
u(x, tk ) = u(x, tk1) + t 0.5 RHS(u(x, tk1)) + 0.5 RHS(u(x, tk ))
u(x, tk ) 0.5 t RHS(u(x, tk )) = u(x, tk1 ) + 0.5 t RHS(u(x, tk1))
2D(t)
where (t) is a white noise process (i.e. a Gaussian random variables for all t with 0
mean and variance of 1; where each Gaussian random variable is uncorrelated in time).
Since we took u(x, 0) = [0,1] , we can think of the initial condition X(0) as a random
variable itself with uniform distribution.
In the command line, type:
>> avgX = monteCarlo sims(t,x,tau,D,mu t);
After it is finished running, type:
>> movie scpt
to see a movie of how well the solution u(x, t) approximates the noisy system.
The match is pretty good despite the crudeness of the methods (first order).
Other issues to be aware of: i) mesh size isnt large enough (in x or t, ii) conserving
probability with weird boundary conditions, etc.
You can go back and play with the function mu t in the file solve advDif if you are
comfortable with the syntax, but you MUST enlarge your domain and mesh size x
appropriately!
4. Nonlinear PDEs
Nonlinear PDEs are a mess to solve. Here is all I have to say about it. The instabilities
that arise generally call for an implicit method (at the very least) to have any hope of
a reasonable numerical solution. The following sections assume you want an implicit
time-stepping solver.
u
t
u(x,tk )u(x,tk1 )
.
t
The system of ODEs can be written down if you discretize the advection and diffusion
parts with a finite difference method. For example, you could use a centered-difference
method:
o A(x , t)u(x , t) A(x , t)u(x , t)
n
j+1
j+1
j1
j1
A(xj , t)u(xj , t) =
x
2x
o D(x )u(x , t) 2D(x , t)u(x ) + D(x )u(x , t)
2 n
j+1
j+1
j
j
j1
j1
D(x
)u(x
,
t)
=
j
j
x2
x2
Care must be taken with the boundary conditions. Again, you might want to use XPP if
your boundary conditions are not nasty.
There are many good nonlinear ODE solvers once you have properly discretized the
system (e.g., CVODE, ode15s, etc.).