8. Ecuaciones diferenciales
En este capítulo, primero veremos algunos métodos básicos. Luego repasaremos brevemente un método de Runge-Kutta de segundo orden. Plantearemos el problema de la resolución de un sistema de ecuaciones diferenciales que surge en cinética química formal.
8.1. El método de Euler
El método de Euler es uno de los más sencillos. Dadas una ecuación diferencial en la forma y’=f(x,y), la condición inicial (de contorno) de que la función y pase por el punto (x0,y0) y el paso de integración h, se calculan los sucesivos valores de y, {yk}, de la siguiente manera
yk+1 = yk + hf(xk,yk) (1)
siendo xk=xk-1+h.
Esta formulación es equivalente a considerar la expansión en serie de Taylor de la función y(x) hasta primer orden. Claro está que el método sólo es exacto para funciones lineales. El error de magnitud en yk+1 es
)
( )
ξε 2 2
21h y
= siendo xk < ξ < xk+1.
Esta fórmula indica que es conveniente tomar pasos de integración h
pequeños. Esto, sin embargo, implica el hecho de que para hacer la integración en un intervalo prefijado se tengan que acumular muchos resultados parciales a través de las sumas en (1), lo cual también va en detrimento de la precisión final del cálculo.
8.2. Métodos de Runge-Kutta
Se puede entender el método básico de Runge-Kutta como una modificación del anterior. La fórmula fundamental es
yk+1 = yk + hf(xk+h/2 , yk+hf(xk,yk)/2 ).
Se observa como aquí no se considera la pendiente de la función en el punto xk sino en el punto medio entre xk y xk+1, es decir el punto xk+h/2. Esta pequeña corrección permite ganar precisión en el cálculo puesto que la derivada que se aplica se puede interpretar como un valor medio de las derivadas reales en los puntos xk y xk+1.
Una fórmula muy popular que explota la idea anterior y que da errores de quinto orden en h es la siguiente:
3 61 2 31 1 31 61 1 y R R R R yk+ = k + + + + donde
(
)
(
)
(
)
(
2)
3 1 2 1 , 2 / , 2 / 2 / , 2 / , R y h x hf R R y h x hf R R y h x hf R y x hf R k k k k k k k k + + = + + = + + = = 8.3. Métodos predictores-correctoresLos métodos predictores-correctores utilizan una fórmula predictora, P, que permite evaluar la coordenada yk del paso en el que nos encontramos. Luego este resultado se refina con una fórmula correctora, C, mediante un proceso iterativo que involucra a la ecuación diferencial. El algoritmo genérico para la integración de la función en el intervalo [a,b] es el que sigue:
1. Se fija una precisión ε. 2. k=0. x0=a. y0=y(x0)
3. Se parte de un punto (xk,yk).
4. Se calcula xk+1. Si xk+1>b se para el proceso.
5. Mediante la aplicación del predictor P se evalúa ( )i k y +1. 6. Se calcula el valor
(
( )i)
k k k f x y y' 1 1 1 +, + + = .7. Mediante el corrector se corrige ( )i k y +1 para dar ( )1 1 + + i k y . 8. Si ( )+ − ( )+ >ε + ki i k y y 1 1
1 entonces yk( )i+1←yk( )i++11 y se pasa de nuevo a 6.
9. Definitivamente, ( )1 1 1 + + + = ki k y y .
10. k←k+1 y se pasa a 4 para evaluar el siguiente punto. El método predictor-corrector más simple es el de Euler, para este:
- La fórmula predictora P es yk+1 =yk +hf
(
xk,yk)
. - La fórmula correctora C es ( )[
(
)
(
( )i)
]
k k k k k i k f x y f x y h y y 1 1 1 1 , , 2 + + + + = + + .(
)
( )
(
)
( )
3 2 1 2 1 1 3 2 1 2 1 1 h O l l z z h O k k y y n n n n + + + = + + + = + + donde(
)
(
)
(
)
(
1 1)
2 1 1 2 1 1 , , , , , , , , l z k y h x hg l l z k y h x hf k z y x hg l z y x hf k n n n n n n n n n n n n + + + = + + + = = =El procedimiento se inicia considerando un punto inicial de partida (x0,y0,z0) y un valor de paso h.
Ejercicios
1. Programar el método de Euler y resolver la ecuación diferencial y’=y en el intervalo [0,1] sabiendo que y(0)=1. Tomar como paso de integración h=0.01. Comparar el resultado con la solución exacta: y=ex.
2. Programar el método de Euler, el de Runge-Kutta y el método predictor-corrector de Euler para resolver la ecuación diferencial y’=y en el intervalo [0,10] sabiendo que y(0)=1. Tomar un paso de integración h=1.0. Comparar cada resultado con la solución exacta: y=ex. En la gráfica que sigue se muestra el comportamiento de cada método. El más preciso es el de Runge-Kutta, que da una función solución que se confunde visualmente con la exacta.
1.0 2.0 3.0 4.0 5.0 6.0 7.0 8.0 9.0 10.0 Eje X 0 10000 20000 30000 40000 50000 60000 Va lo r d e la func ión y ( x ) Euler Euler predictor-corrector Runge-Kutta
Aplicación a sistemas de ecuaciones cinéticas
Como ejemplo de aplicación, resolveremos numéricamente el problema de una reacción cinética que obedezca al siguiente mecanismo:
C B
A →k1 →k2 .
Esto plantea el siguiente sistema de ecuaciones diferenciales:
[ ]
[ ]
[ ]
[ ]
[ ]
[ ]
k[ ]
B dt C d B k A k dt B d A k dt A d 2 2 1 1 = − = − = Si k1≠k2 y [B]0=[C]0=0, la solución exacta es[ ] [ ]
[ ]
[ ]
(
)
[ ] [ ]
(
)
− − + = − − = = − − − − − t k t k t k t k t k e k e k k k A C e e A k k k B e A A 2 1 2 1 1 1 2 2 1 0 0 1 2 1 0 1 1Estas funciones de concentración se representan en la gráfica siguiente para [A]0=1M: 0.0 1.0 2.0 3.0 4.0 5.0 6.0 Tiempo (s) 0.0 0.2 0.4 0.6 0.8 1.0 Concentr a ci ó n (M) A B C
[ ]
[ ]
[ ]
[ ]
k[ ]
B dt C d B k e A k dt B d kt 2 2 0 1 1 = − = −Comparar el resultado gráfico con la solución exacta. Considerar [A]0=1M, [B]0=[C]0=0, k1=1.0 s-1 y k2=2.0 s-1. Integrar para un tiempo total de 6 s.
Programas
*--- program Euler
implicit double precision (a-h,o-z) h=0.010d0 ! Paso de integracion xk=0.0 ! Punto inicial
yk=1.0d0 !
do while (xk<1.0d0) ! Hasta el final! fxy=yk ! La derivada es igual a y xk=xk+h ! Siguiente valor de x yk=yk+h*fxy ! Segun Euler
write(*,’(3g14.6)’) xk,yk,dexp(xk) end do end *--- !--- program Runge_Kutta
implicit double precision (a-h,o-z) h=1.0d0 h2=h/2 xk=0.0d0 ! Punto inicial yk=1.0d0 ! b=10.0d0 ! Punto final do while (xk<b)
R =h*derivada(xk ,yk) ! La derivada R1=h*derivada(xk+h2,yk+R/2) R2=h*derivada(xk+h2,yk+R1/2) R3=h*derivada(xk+h ,yk+R2) xk=xk+h yk=yk+R/6+R1/3+R2/3+R3/6 write(*,'(3g14.6)') xk,yk,dexp(xk) end do
!--- program Euler_predictor_corrector
implicit double precision (a-h,o-z) h=1.0d0 ! Paso h
h2=h/2
epsilon=1.0d-8 ! Precision a=0.0d0 ! Punto inicial b=10.0d0 ! Punto final
xk=a ! Condicion de contorno yk=1.0d0 ! do while (xk<b) xk1=xk+h yk1i=yk+h*derivada(xk,yk) ! Predictor ! Proceso iterativo 1 yk1p=derivada(xk1,yk1i) yk1i1=yk+h2*(derivada(xk,yk)+derivada(xk1,yk1i)) ! Corrector if (abs(yk1i1-yk1i)>epsilon) then yk1i=yk1i1 goto 1 end if
yk=yk1i1 ! Nuevo punto xk=xk1 write(*,'(4g14.6)') xk,yk,dexp(xk),(yk-dexp(xk))/dexp(xk)*100 end do end !--- !--- double precision function derivada(x,y)
implicit double precision (a-h,o-z) derivada=y
end
*--- PROGRAM Runge_Kutta_segundo_orden parameter (zero=0.0e0,one=1.0e0,two=2.0e0) * ao=one xo=zero xf=6.0e0 xk1=one xk2=two yn=zero zn=zero * open(unit=1,file='b.dat',status='unknown') open(unit=2,file='c.dat',status='unknown') * nt=1000
h=(xf-xo)/nt ! 1000 cortes en el intervalo [0,6] xn=xo * write(1,'(2g14.6)') xn,yn write(2,'(2g14.6)') xn,zn do n=1,nt rk1= h * (xk1*ao*exp(-xk1*xn)-xk2*yn) rl1= h * (xk2*yn) xn=xn+h ! Ya es xn1 rk2= h * (xk1*ao*exp(-xk1*xn)-xk2*(yn+rk1)) rl2= h * (xk2*(yn+rk1)) yn1=yn+(rk1+rk2)/2 zn1=zn+(rl1+rl2)/2 write(1,'(2g14.6)') xn,yn1 write(2,'(2g14.6)') xn,zn1 yn=yn1 zn=zn1 end do close(1) close(2) END