LibroMatlabWEB.pdf

July 25, 2017 | Author: Jorge Robet Flores Vilcapoma | Category: Matrix (Mathematics), Array Data Structure, Matlab, Determinant, Computer File
Share Embed Donate


Short Description

Download LibroMatlabWEB.pdf...

Description

Matlab en cinco lecciones de Num´erico V´ıctor Dom´ınguez B´aguena

Ma Luisa Rap´un Banzo

Febrero de 2006

Disponible en http://www.unavarra.es/personal/victor dominguez/

r do rra Bo

Prefacio

El origen de este libro es una asignatura de libre elecci´on que uno de los autores imparti´o durante los cursos 2004–2005 y 2005–2006 en la Universidad P´ ublica de Navarra. Nuestra intenci´on original era tratar temas algo avanzados de C´alculo Cient´ıfico y utilizar Matlab como v´ıa para su aprendizaje. Los alumnos, obviamente, estaban m´as interesados en aprender Matlab y ve´ıan el Num´erico como forma de probar y ensayar las diferentes herramientas de Matlab que se iban exponiendo en clase. Desafortunadamente, la formaci´on en Num´erico de nuestros alumnos nos oblig´o a relajar considerablemente el contenido matem´atico del curso y a ser m´as modestos, desde el punto de vista te´orico, en nuestros objetivos. El resultado final en su vertiente matem´atica se podr´ıa enmarcar sin problemas en un curso introductorio de C´alculo Num´erico. En cuanto a Matlab, creemos que hemos tratado todos sus aspectos fundamentales aunque en ocasiones sea de forma superficial. Nuestro objetivo era conseguir no tanto un conocimiento muy profundo de Matlab como el de colocar al alumno en una buena posici´on de arranque para un autoaprendizaje. El enfoque y los temas tratados son consecuencia de diversos factores entre los que conviene citar nuestro propio bagaje matem´atico1 , el uso que hemos tenido que hacer de Matlab en nuestra carrera investigadora y, como ya hemos mencionado, los conocimientos de partida que ten´ıan nuestros propios alumnos. Hemos insistido bastante en la manip´ ulaci´on de vectores y matrices y a la programaci´on en forma vectorizada. Esta es una de las diferencias m´as acusadas con los lenguajes de programaci´on tradicionales y una implementaci´on eficiente en Matlab pasa necesariamente por la vectorizaci´ on. Los apuntes est´an organizados en torno a temas o lecciones, cada cual dividido en dos partes, la primera de Matlab y la segunda con un tema espec´ıfico de C´alculo Num´erico. En la primera parte se presentan los aspectos instrumentales de Matlab que utilizaremos en la implementaci´on de los algoritmos de la parte de Num´erico. La longitud de cada parte es variable, y dependiente de la dificultad tratada ya sea en la parte instrumental (Matlab) o en la parte matem´atica. De tanto en tanto nos hemos permitido hacer algo de Matem´aticas tratando de presentarlas en la forma m´as simple posible. A lo largo de estas p´aginas el lector podr´a encontrar ejercicios, algunos de ellos resueltos, que tratan de ahondar en puntos espec´ıficos, matem´aticos e inform´aticos. Finalmente se han introducido algunas notas hist´oricas que describen brevemente la evoluci´on que han tenido las ideas a lo largo del tiempo. Con ello tratamos de combatir la idea gaussiana, demasiado extendida, de las Matem´aticas como un mundo est´atico, monol´ıtico y perfecto donde la teor´ıa se presenta cerrada y completa. Las Matem´aticas en general y el C´alculo Cient´ıfico en particular recorren un largo trecho antes de llegar a este estado, durante el cual brotan ideas constantemente, siempre prometedoras en un primer momento, que 1

modelado por nuestra formaci´ on cient´ıfica, com´ un en muchos aspectos.

i

r do rra Bo

evolucionan con los a˜ nos, con muchas de ellas desechadas finalmente e incluso algunas rescatadas a˜ nos despu´es de considerarse como v´ıas muertas. Hemos adjuntado al final una bibliograf´ıa utilizada en este texto. Nos gustar´ıa resaltar tres textos sobre los dem´as. En primer lugar, Numerical Computing with Matlab, de Cleve Moler, que descubrimos cuando and´abamos en la redacci´on de la Lecci´on II. Su sencillez y la buena elecci´on de ejemplos ha ejercido una influencia considerable en estas notas. El segundo libro es ya un cl´asico entre los que aprendimos Matlab hace algunos a˜ nos. And´abamos entonces en la b´ usqueda de recursos en la web cuando nos encontramos con unos apuntes muy completos de libre divulgaci´on. Nos referimos al libro de Garc´ıa de Jal´on y sus colaboradores, Aprenda Matlab ?.? como si estuviera en primero. Diferentes versiones de estos apuntes llevan cubriendo de forma incansable la evoluci´on de Matlab desde la versi´on 4.0. Por u ´ltimo, aunque no es un texto propiamente, la enciclopedia libre on line Wikipedia2 ha sido utilizada profusamente para obtener datos y fuentes utilizadas en la redacci´on de este texto. Debemos se˜ nalar que estas informaciones han sido debidamente contrastadas. A pesar de algunos problemas iniciales, es seguro que la influencia de esta enciclopedia libre crecer´a exponencialmente en el futuro. Finalmente, queremos dejar patente nuestro agradecimiento al Profesor Javier Sayas que se ofreci´o muy generosamente a revisar este libro. Sus numerosas y acertadas indicaciones y sugerencias han contribuido, y mucho, en la redacci´on final de este texto.

Pamplona, Febrero de 2006

2

V´ıctor Dom´ınguez B´aguena un Banzo Ma Luisa Rap´

http://www.wikipedia.org

ii

r do rra Bo A Javier Amigo y maestro.

r do rra Bo

r do rra Bo

Cap´ıtulo 1

Introducci´ on

... and the first lesson of all was the basic trust that he could learn. It is shocking to find how many people do not believe they can learn, and how many more believe learning to be difficult.

Dune Frank Herbert

1.1.

¿Qu´ e es?

Matlab es un entorno de trabajo para el c´alculo cient´ıfico. Programado originalmente por Cleve Moler a finales de los a˜ nos 70, su finalidad original era proporcionar una forma sencilla de acceder a las librer´ıas LINPACK y EISPACK donde est´an implementadas de una forma altamente eficiente los algoritmos clave del an´alisis matricial1 . De hecho, Matlab es una abreviatura de Matrix Laboratory Su primera implementaci´on se hizo en Fortran que era, y en buena medida a´ un sigue si´endolo, el lenguaje est´andar en la implementaci´on de m´etodos num´ericos2 . Posteriormente se reimplement´o en C, que es como se encuentra en la actualidad. Las aplicaciones de Matlab se fueron extendiendo a otras ramas del c´alculo cient´ıfico y de las ciencias aplicadas en general, dot´andole de una gran popularidad en ambientes cient´ıficos (especialmente en Ingenier´ıa). Dichas extensiones se consiguieron en gran parte mediante la implementaci´on de toolboxes, librer´ıas escritas en el lenguaje de programaci´on propio de Matlab y que ampliaban el rango de problemas que pod´ıan resolverse. Sin miedo a equivocarse, se pueden enunciar las siguientes ´areas donde Matlab muestra un gran potencial: ´algebra lineal num´erica;

procesamiento de se˜ nales (an´alisis, compresi´on de datos,..);

1

por ejemplo, el m´etodo de Gauss, el c´alculo de las descomposiciones m´as habituales del ´algebra matricial num´erica (LU , LL> , QR), m´etodos iterativos,... 2 Fortran significa Formula translation. Desarrollado por IBM en 1954, es considerado como el primer lenguaje de alto nivel. Las u ´ltimas actualizaciones (Fortran 95 y Fortran 2003) han dado nuevo vigor a este veterano lenguaje de programaci´ on.

1

dise˜ no de sistemas de control; salidas gr´aficas; estad´ıstica;

r do rra Bo simulaci´on de sistemas din´amicos.

La extensa gama de problemas que cubre hace de Matlab un lenguaje dif´ıcil de entender y manejar en su completitud. Esto no quiere decir que sea inarbodable: el conocimiento base que permite empezar a trabajar es muy sencillo. No obstante el elevado n´ umero de 3 comandos que se encuentra a disposici´on del usuario provoca que en ocasiones existan problemas no s´olo para encontrar los comandos adecuados sino tambi´en para tener una idea de qu´e posibilidades exactamente ofrece Matlab en un problema o tarea en particular.

1.2.

¿C´ omo trabaja?

El lenguaje de programaci´on de Matlab es bastante m´as flexible que el de los lenguajes tradicionales. No es preciso la declaraci´on inicial de variables, ´estas se pueden introducir en el momento que se necesiten, y por ejemplo, vectores y matrices pueden declararse sin especificar sus dimensiones e incluso cambiar sus tama˜ nos sobre la marcha. Ello permite una programaci´on algo m´as desordenada, aunque debe tenerse bien claro que una programaci´on cl´asica, m´as al uso, suele generar c´odigo m´as eficiente. Por otro lado, una gran cantidad de m´etodos num´ericos se encuentran implementados de una forma muy eficiente y son accesibles como simples comandos. De esta forma, Matlab se puede utilizar como una caja negra: el usuario pregunta y el ordenador responde sin que ´este tenga que preocuparse de qu´e tipo de operaciones se han efectuado por el camino. De todas formas es conveniente tener una idea de qu´e m´etodos se est´an utilizando para as´ı ser conscientes de en qu´e condiciones van a funcionar, cu´al es en cada caso el m´etodo adecuado, y especialmente el significado de los, posiblemente, numerosos argumentos opcionales que controlan el funcionamiento del algoritmo. A priori se pueden distinguir dos tipos de funciones en Matlab: funciones compiladas (Built in functions) y funciones no compiladas. Las primeras est´an optimizadas, son programas ya compilados y con el c´odigo no accesible para el usuario. Como ejemplos se pueden citar operaciones fundamentales +, *,. . . .

las funciones matem´aticas b´asicas (sin, cos, exp, log,. . . )

´ algoritmos b´asicos del Algebra Lineal (inv, det, lu, chol, qr,...) s´alidas gr´aficas (plot, surf,...)

3

A modo de ejemplo, estos comandos cubren salidas gr´aficas: plot, line, ezplot, ezsurf, surf, surfc, line, patch, plot3, contour, contourf, ezcontour, pcolor, trimesh, trisurf,...

2

r do rra Bo

Las funciones no compiladas est´an escritas siguiendo el lenguaje de programaci´on propio de Matlab. Estos comandos se guardan en ficheros *.m que es la extensi´on est´andar de los ficheros de Matlab4 . Originalmente, Matlab funcionaba como un interprete. Es decir, cada l´ınea de c´odigo era traducido antes de su ejecuci´on. Ello hac´ıa que una programaci´on similar a lenguajes cl´asicos de programaci´on diera lugar a c´odigo poco eficiente. Este problema se puede subsanar en gran medida recurriendo a la programaci´on vectorizada. El siguiente ejemplo muestra las diferencias con una programaci´on est´andar No vectorizada

Vectorizada

y=zeros(1,1000); h=2*pi/999; for i=0:999 y(i+1)=sin(h*i); end

y=sin(linspace(0,2*pi,1000));

En la primera parte del c´odigo, encontramos una estructura t´ıpica en los lenguajes de programaci´on: el comando for. Su significado es claro: las l´ıneas comprendidas entre el for y end se repiten 1000 veces con la variable i tomando valores de 0 a 999. El resultado final es el vector fila y que recoge el valor del seno en 1000 puntos uniformemente espaciados en [0, 2π]. Por otro lado, el comando linspace devuelve un array que contiene 1000 puntos equidistantes entre 0 y 2π. La funci´on seno es aplicada sobre todo el array devolviendo un vector con estos valores que se guarda en y. La diferencia entre ambas formas de programar es ahora patente. Mientras que en la primera realizamos 1000 llamadas a la funci´on seno con un argumento por llamada, en la segunda hay una u ´nica llamada donde se requiere el c´alculo del seno en 1000 puntos, y el resultado se devuelve en un vector con estos valores (y por tanto tambi´en de longitud 1000). Desde el punto de vista de Matlab el segundo c´odigo es m´as eficiente. Habitualmente, la vectorizaci´on lleva consigo una reducci´ on del c´odigo a la vez que se incrementan las necesidades de memoria. Con Matlab 6.5 se inici´o un proyecto a m´as largo plazo consistente en la aceleraci´on (Performance Acceleration) de las versiones no vectorizadas dirigida a estrechar las diferencias con los lenguajes cl´asicos de alto nivel como Fortran, C o Pascal5 . En cualquier caso, la posibilidad de ejecutar instrucciones en bloque sobre vectores o matrices, en contraste con operaciones elemento a elemento como en los lenguajes tradicionales, es algo que conviene explotar por las importantes ventajas que proporciona. 4

Tambi´en est´ a la extensi´ on *.mat, propia de ficheros de datos. De hecho en la version 6.5 apenas hay diferencias en tiempo de ejecuci´on entre los dos c´odigos expuestos. 5

3

1.3.

¿C´ omo aprenderemos?

r do rra Bo

Como ya hemos se˜ nalado anteriormente, aprender a manejar Matlab en su totalidad est´a fuera de los contenidos de un curso introductorio como ´este. No as´ı aprender los fundamentos y preparar el terreno para un autoaprendizaje de las partes en las que cada uno est´e interesado. Encontramos en este punto dos dificultades que salvar: saber de la existencia del comando adecuado y aprender a utilizarlo. En no pocas ocasiones, la primera es la mayor dificultad. No obstante los comandos llevan siempre nombres nemot´ecnicos para facilitar su memorizaci´on. Las funciones de ayuda tambi´en echan una mano. Como a programar se aprende programando, comenzaremos escribiendo c´odigo desde los primeros pasos. Los esquemas num´ericos que implementaremos se encuentran pr´acticamente en cualquier curso introductorio de An´alisis Num´erico. En cada lecci´on implementaremos dichos algoritmos, introduciendo ´ordenes, estructuras de decisi´on, datos,... seg´ un sea necesario. En los apuntes se incluyen m´ ultiples ejercicios cuya realizaci´on ayudar´a al aprendizaje de la asignatura. Estos apuntes no deben tomarse como un manual en el estilo usual, sino como una forma de aprender Matlab y repasar o aprender el An´alisis Num´erico b´asico. Ya existen manuales extensos y concienzudos, en la bibliograf´ıa citamos algunos de ellos, que pueden servir para ese fin.

4

r do rra Bo Lecci´on I

Primeros pasos en Matlab. M´etodos directos para sistemas de ecuaciones lineales

5

r do rra Bo

r do rra Bo

Introducci´ on

When asked whether a programming language supports matrices, many people will think of two-dimensional arrays and respond, “Yes.” Yet matrices are more than two-dimensional arrays -they are arrays with operations. It is the operations that cause matrices to feature so prominently in science and engineering G.W. Stewart, Matrix Algorithms

Comenzaremos en la primera parte de esta lecci´on tratando nociones b´asicas de Matlab, introduciendo el entorno de trabajo y las estructuras b´asicas de programaci´on. En segundo lugar entraremos en uno de los detalles fuertes de Matlab, la manipulaci´on de vectores y matrices. En la parte matem´atica estudiaremos m´etodos directos para la resoluci´on de sistemas de ecuaciones lineales. En la implementaci´on de estos algoritmos repasaremos los conocimientos de Matlab expuestos en la primera parte.

7

r do rra Bo

r do rra Bo

Cap´ıtulo 2

Matlab: Primeros pasos 2.1.

Entorno de trabajo

En las primeras secciones comenzaremos explorando Matlab de la forma m´as simple, en modo comando: el usuario pregunta y Matlab responde. El interfaz de Matlab es bastante pobre, con un aspecto est´etico que en modo alguno es comparable al de programas como Maple o Mathematica. El modo interactivo de trabajar es sencillo aunque algo inc´omodo. A modo de ejemplo, requiere algo de esfuerzo editar instrucciones ejecutadas con anterioridad ´ y manejarse con bloques de comandos es muy engorroso. Este y otros problemas del modo interactivo se subsanan en gran medida empaquetando instrucciones con ficheros script y/o programando en funciones (subrutinas) que es la forma natural de trabajar en Matlab. En un segundo paso, se puede implementar un interfaz gr´afica, las guides de Matlab, que hacen m´as amigable la comunicaci´on con el usuario. En la Figura 2.1 podemos ver el aspecto inicial de Matlab. Distinguimos las siguientes ventanas Command window: ventana donde podemos ejecutar los comandos;

Ventanas auxiliares: command history, workspace, current directory que informan sobre (y permiten editar) los comandos insertados, las variables declaradas y el directorio en el que estamos trabajando. Ventana de ayuda: en una ventana independiente proporciona un acceso completo a las funciones de ayuda de Matlab, incluyendo b´ usquedas, demostraciones, etc.

´ Estas son las caracter´ısticas b´asicas que debemos considerar:

El prompt de Matlab es >>. El usuario escribe a continuaci´on. Para ejecutar se pulsa la tecla Enter.

Se pueden recuperar comandos anteriores navegando con las flechas ↑ y ↓.

Cuando se trabaje en Matlab, debemos tener muy en cuenta que: Se distinguen may´ usculas y min´ usculas. 9

´ I LECCION

2.1 Entorno de trabajo

r do rra Bo Figura 2.1: Pantalla Principal.

Todos los comandos de Matlab se escriben en min´ usculas y los argumentos se env´ıan entre par´entesis separados por comas.

El car´acter % se utiliza para insertar comentarios. Todo lo que sigue (en la misma l´ınea) es ignorado por Matlab.

Si se teclea al final de una instrucci´on ’;’ ´esta se ejecuta pero el resultado no se visualiza por pantalla.

Dos comandos se pueden insertar en la misma l´ınea separados por “,” o por “;”. La diferencia entre los dos es que con “,” se muestran los resultados de las operaciones mientras que con “;” la operaci´on se ejecuta pero no se visualiza.

Ejercicio 2.1 Ejecuta las instrucciones >> >> >> >> >>

4+4 % mi primera operacion 3^4, 4/9 3^4; 4/9 3^4, 4/9; 3^4; 4/9;

10

´ I LECCION

Cap´ıtulo 2. Matlab: Primeros pasos

y observa la salida. Haremos algunos comentarios sobre el ejercicio anterior. El circunflejo ^ es la potenciaci´on: >> 3^5

r do rra Bo ans=

243

El t´ermino ans es la primera variable que vemos de Matlab. Concretamente, guarda la u ´ltima salida dada por Matlab (answer): >> 4+6 ans =

10

>> ans*2 ans =

20

>> ans*2 ans =

40

La ra´ız cuadrada se puede calcular bien elevando a 1/2 (^(1/2)) o bien utilizando sqrt. Ejercicio 2.2 Comprueba la diferencia entre 4/4+6

4/(4+6)

3^5*2

3^(5*2)

Nota. La prioridad de ejecuci´on entre operaciones matem´aticas es la habitual: primero se calcula la potenciaci´on ^, posteriormente los productos y divisiones *, / y en u ´ltimo lugar, las sumas y restas + y -. Este orden se puede cambiar utilizando los par´entesis. La regla es sencilla: dada una expresi´on, lo primero que se calcula es lo que est´a dentro de cada par´entesis. Esta regla es recursiva, es decir, si dentro de un par´entesis hay otros par´entesis, para evaluar el primero se empezar´a con los par´entesis interiores.  Los n´ umeros reales se pueden insertar tambi´en en notaci´on cient´ıfica, muy adecuada si se trata de n´ umeros grandes o muy peque˜ nos (en valor absoluto). As´ı, se tiene la siguiente regla de construcci´on: m · 10r m er 11

´ I LECCION

2.1 Entorno de trabajo Por ejemplo 0.005 −1201200000

115 · 1012 0.00031415

5e − 3 −1.2012e009

115e12 3.1415e − 004

r do rra Bo

Existen adem´as dos n´ umeros especiales: inf y NaN. El primer signo representa la cantidad infinita (∞). El segundo es una abreviatura de “no es un n´ umero” (Not a Number) y es el resultado que se devuelve ante una operaci´on indefinida como 0/0. Este s´ımbolo se puede utilizar en ´ambitos, en principio tan extra˜ nos, como en el dibujo de superficies (v´er la Lecci´on V). En general los resultados num´ericos se presentan con cuatro cifras decimales correctas, aunque todas las operaciones se ejecutan en doble precisi´on1 . Si se desean las salidas con toda la precisi´on disponible se debe insertar la instrucci´on >> format long

A partir de este punto, el resultado de cualquier operaci´on se mostrar´a con 16 cifras significativas. La instrucci´on >> format short

devuelve a la forma est´andar con cuatro cifras decimales. Existen m´as opciones con format. Las siguiente l´ıneas muestran algunas de ellas: >> pi % el numero pi ans =

3.1416

>> format long >> pi

% mayor precision

ans =

3.14159265358979

>> format compact % compacto >> pi ans = 3.14159265358979 >> format bank %No fijo de cifras decimales >> pi ans = 3.14

1

Aproximadamente 16 cifras decimales correctas. En el momento de redactar estas l´ıneas, los procesadores de 32 bits dominan todav´ıa el parqu´e de ordenadores. Las nuevas generaciones, con procesadores con 64 bits, duplican la precisi´ on de trabajo.

12

´ I LECCION

%salidas en forma fraccionaria

% mas espaciada

r do rra Bo

>> format rat >> pi ans = 355/113 >> format loose >> pi

Cap´ıtulo 2. Matlab: Primeros pasos

ans =

355/113

Observa la diferencia de espaciamiento que se obtiene con las opciones compact y loose.

N´ umeros complejos

La √ aritm´etica compleja se encuentra tambi´en integrada en Matlab. La unidad imaginaria ( −1) se representa en Matlab con i ´o j: >> clear i j % borramos posibles valores de i y j >> i^2 ans=

-1

>> j^2 ans=

-1

El signo i suele ser habitual en Matem´aticas mientras que en diversas ramas de la F´ısica y en Ingenier´ıa de Telecomunicaciones o El´ectrica se prefiere el s´ımbolo j (en este caso para no confundir con la intensidad de corriente el´ectrica). De ah´ı que Matlab permita ambas representaciones. Todas las operaciones matem´aticas incluyen la aritm´etica compleja en el sentido usual >> 1+i +5-6i

% suma de dos numeros complejos

ans =

6.0000 - 5.0000i

>> (5+3i)*(5-3i), (1+2i)/(3-4i) ans =

13

´ I LECCION

2.2 Comandos de ayuda 34.00

ans =

r do rra Bo

-0.20

+

>> conj(3e-3+2e-4i) % conjugado ans =

0.0030 - 0.0002i

>> abs(3+4i),

angle(2i)

% modulo y argumento

ans =

5

ans =

1.5708

2.2.

Comandos de ayuda

La ayuda de Matlab es ciertamente muy clara y completa. Los comandos siempre dispuestos a echarnos una mano son: help: muestra una ayuda por pantalla, en la ventana de comandos, con la informaci´on esencial sobre un comando concreto.

helpwin: similar a help pero despliega la ayuda en una ventana auxiliar, permitiendo as´ı una navegaci´on, estilo web, muy c´omoda. lookfor: permite buscar una cadena en la primera l´ınea de todos los ficheros de ayuda.

Por ejemplo, si deseamos ayuda sobre la funci´on sin, podemos ejecutar >> help sin

SIN Sine. SIN(X) is the sine of the elements of X. Overloaded methods help sym/sin.m 14

´ I LECCION

Cap´ıtulo 2. Matlab: Primeros pasos

r do rra Bo Figura 2.2: Pantalla de ayuda.

o bien

>> helpwin sin

y obtener la pantalla que se muestra en la Figura 2.3. Adem´as, si aparece el enlace “Go to online doc for ...”, ´este nos permite navegar entre una ayuda mucho m´as completa donde se muestran ejemplos y detalles sobre la implementaci´on del comando (ver la Figura 2.42 ).

Ejercicio 2.3 Utilizando las funciones de ayuda, obtener informaci´on de alguna de estas funciones elementales de Matem´aticas sin sec sinh exp

cos csc cosh log

tan cot tanh log10

asin asec asinh log2

acos acsc acosh sign

atan acot atanh

Mediante la instrucci´on 2

Para que esta opci´ on est´e disponible es necesario que se haya instalado la ayuda completa de Matlab. A partir de la versi´ on 6.0 la instalaci´ on consta de (al menos) dos CDs, el primero con el programa y las librer´ıas habituales y el segundo con la documentaci´on de la ayuda.

15

´ I LECCION

2.3 Variables

r do rra Bo Figura 2.3: Ayuda con helpwin. Comprueba si aparece la opci´on Go to online doc... >> help +

se pueden adem´as visualizar las operaciones “elementales” seg´un Matlab.

2.3.

Variables

Matlab no necesita la declaraci´on de variables como en un lenguaje tradicional. En principio todas las variables son reales, y basta hacer uso de ellas para que queden declaradas: >> a=1; b=2; c=3; >> a-b ans =

-1

>> a*b*c ans = 16

´ I LECCION

Cap´ıtulo 2. Matlab: Primeros pasos

r do rra Bo Figura 2.4: Ayuda on line.

6

El comando who sirve para conocer los nombres de las variables declaradas, mientras que con whos obtenemos una informaci´on m´as precisa: >> who

Your variables are: a

b

c

>> whos a Name Size a

Bytes

1x1

8

Class

double array

Grand total is 1 element using 8 bytes Para borrar una variable se utiliza la instrucci´on clear, por ejemplo, 17

´ I LECCION

2.3 Variables >> a=4; >> whos a Size

a

1x1

Bytes

Class

8

double array

r do rra Bo

Name

Grand total is 1 element using 8 bytes

>> clear a >> whos a >>

borra la variable (es decir, whos no devuelve nada). Con la orden >> clear all

se borran todas las variables declaradas hasta el momento. Nota. En Matlab es correcto declaraciones de este tipo >> sin=1; >> sin+1 ans=

2

De esta forma sin pasa a ser una variable que sobrescribe el valor original que ten´ıa como funci´on seno. Para recuperar el valor original basta ejecutar >> clear sin



Almacenamiento de variables en ficheros

Matlab ofrece la posibilidad de grabar las variables que deseemos en un fichero. De esta forma, podemos recuperarlas m´as adelante, ya sea en la misma sesi´on o en otra diferente3 . Por ejemplo >> >> >> >>

a=4+i;% numero complejo b1=cos(2); b2=sin(2); save datos a b1 b2

graba dentro del directorio de trabajo, en un fichero de nombre datos.mat, las variables indicadas. Para recuperar, basta ejecutar >> load

datos

3

Se entiende por sesi´ on el tiempo que transcurre entre que se abre y se cierra Matlab. Al cerrar el programa, todas las variables locales se pierden.

18

´ I LECCION

2.4.

Cap´ıtulo 2. Matlab: Primeros pasos

Ficheros script y funciones

La forma m´as eficiente de empaquetar series de instrucciones simples y mec´anicas es utilizando ficheros script. Tareas m´as elaboradas, con, por ejemplo, variables de entrada y salida, requieren del uso de funciones.

r do rra Bo 2.4.1.

Ficheros script

Un fichero script es un simple documento de texto que contiene una sucesi´on de comandos de Matlab. Esencialmente es equivalente a teclear estas instrucciones directamente en la ventana de comandos. Describiremos el manejo de este tipo de ficheros mediante un sencillo ejemplo. Comenzamos creando un fichero tecleando en modo comando la orden4 >> edit prueba

Se despliega as´ı en una ventana aparte el editor de Matlab con el fichero prueba.m (“.m”es la extensi´on est´andar de Matlab). Es importante saber cu´al es el directorio de trabajo5 , pues es donde se guardar´a por defecto el fichero. Tecleamos ahora en el editor a=1+i; b=1-i; disp(’a*b=’) disp(a*b) disp(’a/b=’) disp(a/b) disp(’sqrt(a)=’) disp(sqrt(a))

El comando disp (de display) muestra vectores por pantalla de forma compacta. Dado que para Matlab un cadena de caracteres es simplemente un vector de car´acteres, se consigue con ello mostrar por pantalla mensajes de forma concisa. Una vez que el documento est´a grabado, para ejecutar las ´ordenes que contiene basta teclear el nombre del fichero en la ventana de comandos: >> prueba

Se puede modificar las veces que se precise las variables a y b en el fichero script sin tener que teclear de nuevo todas las instrucciones.

2.4.2.

Funciones

En principio existen dos tipos de funciones: las funciones inline, que se insertan en la l´ınea de comandos y las que se escriben en un documento de texto externo. Esta u ´ltima forma, que es la evoluci´on natural de los ficheros script, es m´as flexible y es en la que nos centraremos a continuaci´on. Dejaremos pendiente para la Lecci´on III la descripci´on de las funciones inline. Como antes, para crear un fichero que contenga a una funci´on se puede teclear: 4 5

Tambi´en es posible crear este fichero a golpe de rat´ on. Por defecto es C:\MATLAB6p5\work.

19

´ I LECCION

2.4 Ficheros script y funciones >> edit mifuncion En el editor puedes insertar este simple ejemplo: % MIFUNCION % % Y=MIFUNCION(X) devuelve % % Y=X^2-COS(X) % function y=mifuncion(x)

r do rra Bo

01 02 03 04 05 06 07 08 09 10 11

y=x^2-cos(x); return

La funci´on se declara con function, la variable de entrada es x y se declara como variable de salida y. Se termina la ejecuci´on de la funci´on cuando se ejecuta un return o bien se llega al final de la funci´on6 . Ahora, para calcular el valor de π 2 − cos(π) podemos ejecutar la orden: >> mifuncion(pi) ans =

10.8696

Nota. Los n´ umeros correlativos situados a la izquierda no forman parte del c´ odigo de la funci´ on. Han sido insertados con el fin de numerar las l´ıneas y as´ı facilitar los comentarios que podamos hacer sobre el programa.  Una funci´on puede no tener salidas, por ejemplo, 01 02 03 04 05 06 07 08 09 10 11 12 13 14

% INFORMACION % % INFORMACION devuelve informacion sobre % la precision de la maquina % function informacion disp(’precision de la maquina’) disp(eps) disp (’mayor numero real’) disp(realmax) disp (’menor numero real’) disp(realmin) return

6

En este sentido, el return del ejemplo anterior es superfluo.

20

´ I LECCION

Cap´ıtulo 2. Matlab: Primeros pasos

o bien devolver m´ ultiples salidas: % MIFUNCION2 % % [Y1,Y2]=MIFUNCION2(X1,X2,X3) devuelve % % Y1=X1+X2+X3; % Y2=X1-X2+X3; % function [y1,y2]= mifuncion2(x1,x2,x3)

r do rra Bo

01 02 03 04 05 06 07 08 09 10 11 12 13

y1=x1+x2+x3; y2=x1-x2+x3; return

Observa c´omo se recogen los resultados

>> [z1,z2]=mifuncion2(1,2,3); >> z1 ans=

6

>> z2

ans=

2

>> z=mifuncion2(1,2,3);

% Ahora solo devuelve el primero

ans=

6

La cabecera que hemos introducido en el pre´ambulo de las funciones, es decir las l´ıneas anteriores a la declaraci´on de la funci´on y precedidas con “%”, constituyen la ayuda de la funci´on: >> help mifuncion2 MIFUNCION2

[Y1,Y2]=MIFUNCION2(X1,X2,X3) devuelve Y1=X1+X2+X3; Y2=X1-X2+X3; 21

´ I LECCION

2.5 Vectores y matrices

Aunque muy recomendables7 , su inclusi´on en una funci´on es opcional. La ayuda puede estar antes o despu´es de la declaraci´on de la funci´on. En cualquiera de los dos casos, Matlab despliega como ayuda todas las l´ıneas que esten precedidas con % hasta que se encuentra con la primera l´ınea no comentada.

r do rra Bo Nota. Para ser consecuentes, lo correcto es denominar de igual modo a la funci´on y al archivo que la contiene. Sin embargo esto no es obligatorio, es decir, se pueden dar nombres distintos, pero en este caso Matlab da preferencia al nombre del archivo. Aunque Matlab distingue entre may´ usculas y min´ usculas en sus comandos, esto no es extensible para funciones programadas en m-files, al menos en Windows. Es decir, para ejecutar una funci´on en un archivo, digamos, operaciones, se puede utilizar OPERACIONES, Operaciones y cualquier combinaci´on con may´ usculas y min´ usculas. Esto es debido a que el sistema de archivos de Windows tampoco hace esa distinci´on8 . Versiones m´as avanzadas de Matlab, 7.0 en adelante, muestran sin embargo un aviso si no existe una concordancia exacta min´ usculas-may´ usculas entre el nombre del fichero y el comando utilizado para llamarlo. Todas las variables se env´ıan por valor, no por referencia. Es decir, si una funci´on modifica una variable de entrada, esta modificaci´on se pierde cuando finalice su ejecuci´on, recuperando el valor original. Por u ´ltimo, en un fichero se pueden incluir varias funciones. En este caso s´olo la primera funci´on es accesible desde el exterior (l´ınea de comandos, otras funciones,...) mientras que el resto de funciones presentes en ese fichero son internas, es decir, utilizables u ´nicamente por las funciones presentes en el archivo. Esto es importante a la hora de realizar una programaci´on modular. Si un conjunto de funciones son s´olo utilizadas por una funci´on principal, se pueden insertar en el mismo fichero que ´esta. Evitamos as´ı llenar la carpeta de trabajo, o de nuestro proyecto, con ficheros y m´as ficheros. 

2.5.

Vectores y matrices

Dado que principalmente trabajaremos s´olo con arrays de una y dos dimensiones hablaremos en lo que sigue de los objetos matem´aticos correspondientes: vectores y matrices. Todo lo que sigue se puede adaptar a arrays con m´as dimensiones, aunque por simplificar, nos centraremos ahora en el manejo de vectores y matrices y dejaremos pendiente para la Lecci´on IV el uso de arrays multidimensionales (tensores).

2.5.1.

Definici´ on de matrices y vectores

Un vector o una matriz se puede definir dando sus elementos entre corchetes y separando filas mediante “;”. Por ejemplo, las instrucciones 7

No hay que subestimar nunca la capacidad de olvido de uno mismo: el c´odigo claro y legible de hoy es ilegible semanas despu´es. Las ayudas facilitan la edici´on de los programas no s´olo para un usuario externo sino para el propio programador. 8 Es decir, si existe un fichero llamado operaciones.m no es posible crear otro con nombre Operaciones.m

22

´ I LECCION

Cap´ıtulo 2. Matlab: Primeros pasos

>> a=[1 3 -1; 2 3 4; 4 5 1]; >> a2=[1 2 4; -1 0 1; 2 1 5]; >> b=[1; 3; 1]; b2=[-1 1 -2 2]; matrices y vectores    3 −1 1 2 4 3 4  , a2 =  −1 0 1  , 5 1 2 1 5



 1 b =  3 , 1

r do rra Bo

definen las  1  a= 2 4

b2 =



 −1 1 −2 2 .

Matlab distingue entre vectores fila y columna por lo que habr´a que tenerlo en cuenta por ejemplo cuando se desee hacer operaciones como sumas o productos. Desde una vertiente pr´actica, si se va a trabajar con una matriz grande, por ejemplo de tama˜ no 20 × 10, y sus valores se van a introducir m´as adelante, se puede empezar con >> a=zeros(20,10);

A partir de este instante se pueden insertar los elementos, accediendo a cada posici´on mediante par´ entesis >> a(4,5)=9; a(2,1)=6; a(1,1)=-3.4; >> a(4,5) ans=

9

En cualquier caso, si tratamos de introducir un valor en una posici´on no definida de la a ning´ un matriz, Matlab ir´a adaptando el tama˜ no seg´ un juzgue apropiado9 , y no dar´ error. El siguiente ejemplo ilustra esta caracter´ıstica >> clear c % c esta borrado >> c(1,2)=4 % c es ahora 1 x 2 c =

0

>> c(3,3)=2

4

% c pasa a ser 3 x 3

c =

0 0 0

4 0 0

0 0 2

Esta habilidad, aunque permite una programaci´on muy flexible y descuidada, debe utilizarse con mesura dado que puede provocar errores de ejecuci´on muy dif´ıciles de detectar. 9

Ello obliga a que haya que redimensionar constantemente la memoria otorgada a la variable a. Esto supone un costo adicional, inapreciable con ejemplos peque˜ nos, pero importante para grandes cantidades de memoria. Por tanto es mejor declarar primero las dimensiones de la matriz e informar as´ı a Matlab de cu´anta memoria tiene que reservar.

23

´ I LECCION

2.5 Vectores y matrices

2.5.2.

Operaciones

Todas las operaciones habituales entre matrices, tales como la suma, producto, potenciaci´on, c´alculo de determinantes, inversas..., est´an ya implementadas en Matlab. No hay por tanto necesidad de programarse estas tareas. Por ejemplo, si a y a2 son matrices de tama˜ nos compatibles, las instrucciones

r do rra Bo a*a2

a^2

a+a2

devuelven el producto matricial de a y a2, el cuadrado de a (es decir, a*a) y la suma de a y a2. Es importante observar la diferencia con estas l´ıneas a.*a2

a.^2

En el primer caso, se devuelve la matriz resultado de multiplicar elemento a elemento a y a2 (por tanto deben tener el mismo tama˜ no) y en el segundo, una matriz cuyas entradas son el cuadrado de las de a. Esto es una constante en Matlab: el signo “.” indica que la operaci´on (un producto, una potencia o una divisi´on) se hace elemento a elemento, mientras que en caso contrario se calcula la operaci´on matem´ atica, en este caso el producto matricial.

Ejercicio 2.4 Introduce en a y a2 dos matrices de igual tama˜no. Observa el resultado de ejecutar a+a2

a*a2

a.*a2

Define un vector b fila o columna y ejecuta b.^3

b’

Comprueba si estas operaciones est´an bien definidas a*2

a+1

¿Qu´e hacen exactamente? ¿Por qu´e crees que no es necesario “.” en la primera instrucci´on?. Otros comandos importantes son det

inv

/

\

/.

\.

Los dos primeros son el determinante y la inversa de una matriz cuadrada. Los operadores “/” y “\” (slash y backslash) son ciertamente especiales: a/a2 es equivalente a a*inv(a2),

a\a2 es equivalente a inv(a)*a2

En cuanto a su relaci´on con ./ y \. es la misma que ha surgido antes, esto es, aplicado sobre matrices procede a realizar los cocientes elemento a elemento. Requiere por tanto que ambas matrices tengan el mismo tama˜ no. Ejercicio 2.5 Ejecuta las instrucciones >> 3/5 >> 3\5

y observa el resultado. ¿Tiene sentido desde el punto de vista anterior?. Ejercicio 2.6 Dado b una matriz, ¿qu´e hace 1/b?. 24

´ I LECCION

Cap´ıtulo 2. Matlab: Primeros pasos

Nota. El operador backslash “\” se utiliza profusamente para resolver sistemas de ecuaciones lineales, bajo la idea de que Ax = b



x = A−1 b.

As´ı, si b es n × 1 y a es n × n,

r do rra Bo >> x=a\b;

devuelve en x la soluci´on del sistema correspondiente. El funcionamiento real de \ dista mucho de ser tan simple. Esto es, no calcula la inversa de a para multiplicarla por b, sino que resuelve el sistema de ecuaciones por alguna variante del m´etodo de Gauss. Se puede utilizar helpwin mldivide (o helpwin mrdivide para /) para leer en detalle c´omo procede este comando.  Las funciones propias de Matlab trabajan de forma natural sobre vectores y matrices. El resultado final es equivalente a aplicar el comando elemento a elemento. Por ejemplo, >> a=[0 pi/3; -pi/3 0]; >> cos(a) ans =

1.0000 0.5000

0.5000 1.0000

es equivalente a

>> [cos(0) cos(pi/3); cos(-pi/3) cos(0)] ans =

1.0000 0.5000

2.5.3.

0.5000 1.0000

Detalles adicionales

C´ omo obtener las dimensiones de vectores y matrices

Los comandos de Matlab size y length nos proporcionan esta informaci´on: >> a3=[1 2; 3 6; 5 -1]; >> size(a3) ans =

3

2

>> length(a3)

25

´ I LECCION

2.5 Vectores y matrices ans = 3

r do rra Bo

>> a3=a3’; % cambiamos la forma de a3 >> size(a3) ans = 2

3

>> [m,n]=size(a3); % m son las filas y n las columnas >> m ans = 2

>> n

ans = 3

>> length(a3) ans = 3

El comando size devuelve un vector de tama˜ no 2×1 con el n´ umero de filas y columnas del vector/matriz. El resultado es diferente seg´ un se aplique a vectores fila o columna. La orden length devuelve la longitud de una matriz o vector. Su significado en el caso de un vector est´a clara mientras que para matrices devuelve el m´aximo entre el n´ umero de filas y el n´ umero de columnas. Matrices especiales

Matlab dispone de una serie de comandos que permiten construir matrices con una estructura particular. Cabe se˜ nalar las siguientes ´ordenes: eye(n) es la matriz identidad de orden n; ones(m,n) es una matriz m x n de 1s;

zeros(m,n) es una matriz m x n de 0s, esto es, igual que ones pero con ceros; y algunas m´as ex´oticas como hilb, invhilb, pascal, magic. 26

´ I LECCION

Cap´ıtulo 2. Matlab: Primeros pasos

Existen dos formas de introducir vectores cuyos valores siguen una distribuci´on regular a:b:c construye el vector de valores [a a+b a+2*b .... a+k*b] donde a+k*b es el mayor n´ umero natural que cumple a+k*b≤ c. La instrucci´on a:c toma b = 1. linspace(a,b,n) devuelve una partici´on uniforme de [a, b] en n puntos.

r do rra Bo Por ejemplo, >> 0:10 ans=

0 1 2 3 4 5 6 7 8 9 10

>> 10:-1:0 ans=

10

9

8

7

6

5

4

3

2

1

0

>> 0.1:0.3:1.5 ans =

0.1000

0.4000

0.7000

1.0000

1.3000

>> linspace(0,2,4) ans =

0

0.6667

1.3333

2.0000

>> linspace(2,0,4) ans =

2.0000

1.3333

0.6667

0

Nota. Cuando Matlab tiene que devolver un vector y no se le especifica el formato, devuelve una fila. 

2.5.4.

Acceso a partes de matrices

El manejo de partes de vectores y matrices, as´ı como la eliminaci´on de filas o columnas, cambios de tama˜ no, etc, se hace v´ıa instrucciones muy simples en Matlab. Aunque pueda resultar algo extra˜ no al principio, un poco de pr´actica es suficiente para que el usuario se 27

´ I LECCION

2.5 Vectores y matrices

adapte a la nueva sintaxis, tan diferentes a la de un lenguaje tradicional, y pueda utilizarlo en sus c´odigos. Comencemos viendo un ejemplo:

r do rra Bo

>> a=[1 2 3; 4 5 6; 7 8 9; 10 11 12]; >> a(2,3) % elemento (2,3) de a ans =

6

>>a(2,:)

% fila 2 de a

ans =

4

5

6

>>a(:,1)

% columna 1

ans =

1 4 7 10

>>a(:,2)=0 % columna 2 es ahora 0 a =

1 4 7 10

0 0 0 0

3 6 9 12

Podemos acceder a partes de una fila o columna: >> a(1,2:3)

% vector [a(1,2) a(1,3)]

ans =

0

3

>> a(2:4,3)

% vector columna [a(2,3); a(3,3); a(4,3)]

ans =

28

´ I LECCION

Cap´ıtulo 2. Matlab: Primeros pasos

6 9 12 >> a(1:2,2:3) % matriz [a(1,2) a(1,3); a(2,2) a(2,3)]

r do rra Bo ans =

0 0

3 6

En general, si p es un vector de n´ umeros enteros, v(p) devuelve [v(p(1)), v(p(2)), ..., v(p(n))]. Por ejemplo, >> v=[0.1 0.2 0.3 0.4 0.5 0.6]; >> v(4:-1:2) ans=

0.4000

0.300

>> p=[5 1 2 3 3 3]; >> v(p)

0.2000

% no importa que esten repetidos

ans=

0.5000

0.1000

0.2000

0.3000

0.3000

Ejercicio 2.7 Ejecuta las siguientes l´ıneas

>> a=[1 2 3 4; 5 6 7 8; 9 10 11 12]; >> p=[1 3 2]; q=[1 2 1]; >> a(p,q)

¿Qu´e hacen exactamente?.

Igualmente es f´acil a˜ nadir filas y columnas a una matriz: >> a=[1 2 3 4; 5 6 7 8] a =

1 5

2 6

3 7

>> a=[a; [1 -1 2 4]]

4 8

% adosamos una fila nueva

a = 29

0.3000

´ I LECCION

2.6 Bucles y estructuras de decisi´on

1 5 1

2 6 -1

3 7 2

% una nueva columna

r do rra Bo

>> a=[a [0; 2; 4] ]

4 8 4

a =

1 5 1

2 6 -1

3 7 2

4 8 4

0 2 4

Si se desea eliminar una fila o columna se puede utilizar el s´ımbolo vac´ıo []. Por ejemplo, >> a(:,2)=[]

% suprime la segunda columna

a =

1 5 1

3 7 2

4 8 4

0 2 4

Ejercicio 2.8 Programa una funci´on cuyas entradas sean una matriz cuadrada y un t´ermino independiente compatible y que devuelva la matriz ampliada del sistema de ecuaciones lineales. Esto es, una matriz con la matriz original y una u´ltima columna con el t´ermino independiente.

2.6.

Bucles y estructuras de decisi´ on

Claves en cualquier lenguaje de programaci´on, Matlab dispone de varias de ellas entre las que sobresalen for e if, un est´andar en el mundo de la inform´atica.

2.6.1.

Bucles: el comando for

En Matlab, la estructura

for j=inicio:paso:final ..... end

implementa un bucle donde las l´ıneas de c´odigo entre for y end son ejecutadas repetidamente con j tomando los valores del vector inicio:paso:final (v´ease la Secci´on 2.5.3) Por ejemplo, >> for j=1:3; 1

disp(j);

end

30

´ I LECCION

Cap´ıtulo 2. Matlab: Primeros pasos

2 3 disp(j-2);

end

r do rra Bo

>> for j=6:-2:2; 4 2 0

En general, si v es un vector, for j=v ..... end

procede a ejecutar las l´ıneas internas con j tomando los valores del vector v. Por ejemplo, >> v=[2 5 3 1];for j=v; 2

disp(j);

end

5 3 1

Asociados a for, y en general a cualquier bucle, encontramos los comandos break y continue. El primero fuerza la salida inmediata del bucle mientras que el segundo reinicializa la iteraci´on con el siguiente valor del ´ındice. Ejercicio 2.9 La matriz de Hilbert de orden n es  1 12 · · · · · ·  1 1 ··· ···  2 3 A=  .. . . . . . . . . .  .

1 2n−2

1 n

1 n 1 n+1

.. .

1 2n−1

     

Construye la matriz anterior mediante un fichero script y el uso de dos “for” anidados.

2.6.2.

Operadores l´ ogicos y estructuras de decisi´ on

Los operadores l´ogicos m´as b´asicos en Matlab son == igualdad, ~= desigualdad, >= mayor o igual, &

mayor, “y” l´ogico,

< |

menor, “o” l´ogico

´ I LECCION

2.6 Bucles y estructuras de decisi´on El resultado de una comparaci´on es 1 si es verdadero, 0 si es falso: >> a=1; b=2; c=3; >> a>0 ans =

r do rra Bo 1

>> a>0 & b> a test= (a~=0) ans =

1

>> whos test Name

Size

test

1x1

Bytes 1

Class

logical array

Grand total is 1 element using 1 bytes

Estos “0” y “1” no son valores num´ericos sino l´ogicos como se comprueba con la u ´ltima instrucci´on10 . Cuando se aplica a un vector, devuelve un vector de verdadero/falso de la misma longitud que el vector original: >> b=[1 2 -3 -1 2 -4];

p=(b>=1)

% entradas de b>=1

p= 1

1

0

0

1

0

En el ejemplo anterior, p(i)==1 si b(i)≥1 y cero en caso contrario. Ahora, podemos aislar los elementos mayores o iguales que 1 simplemente con 10

Ocupan un u ´nico byte mientras que un n´ umero real utiliza ocho bytes.

32

´ I LECCION

Cap´ıtulo 2. Matlab: Primeros pasos

>> b(p) 1

2

2

Desde este punto de vista es correcta y recomendable utilizar la instrucci´on % elementos de b mayores o iguales que 1

r do rra Bo

>> b(b>=1) 1

2

2

que adem´as resulta muy natural (y f´acil de entender).

Nota. El comando logical puede utilizarse para construir vectores y estructuras l´ogicas a partir de vectores de n´ umeros enteros: >> b=[2 4 6 8 10]; p=[1 0 0 1 >> b(p) % Dara error

1];

??? Subscript indices must either be real positive integers or logicals. >> p=logical(p); >> b(p) ans =

2

8

10

 La estructura de decisi´on, como en muchos otros lenguajes, es if. Su sintaxis es la siguiente: if simple: si la operaci´on l´ogica efectuada es verdadera, se ejecutan las l´ıneas de c´odigo comprendidas entre if y end if (x1) disp(’valor absoluto de x mayor que 1’) end

if compuesto: como el anterior, pero un nuevo conjunto de l´ıneas, comprendidas entre else y end son ejecutadas en caso de que la operaci´on l´ogica efectuada en el if sea falsa: if (x-10) f=x^2; % x entre -10 y 0 else f=sin(x^2); % x menor que -10 o mayor que 0 end 33

´ I LECCION

2.6 Bucles y estructuras de decisi´on if de decisi´on m´ ultiple:

r do rra Bo

if (x 11 b1 d1 . 1 d1 | {z } | {z } (1) (1) A b

El segundo paso del m´etodo de Gauss se aplica ahora sobre la matriz A(1) (de tama˜no (n−1)× (n − 1)) y el vector b(1) (de tama˜no (n − 1) × 1) y as´ı se procede sucesivamente. Implementa esta resoluci´on alternativa del m´etodo de Gauss. (Ayuda. Observa estas tres instrucciones l=a(i+1:n,i)/a(i,i)

a(i+1:n,i+1:n)-l*a(i,i+1:n)

b(i+1:n)-l*b(i)

¿Qu´e hacen?)

Nota sobre la vectorizaci´ on

La noci´on de vectorizaci´on, trabajar con vectores y matrices en lugar de elemento a elemento, no es nueva ni en el An´alisis Num´erico ni en la computaci´on a alto nivel. El objetivo que se persigue es que las todas las operaciones se reduzcan a operaciones matem´aticas sencillas, como productos escalares, productos matriciales, b´ usqueda de m´aximos y m´ınimos en un vector/matriz, suma de vectores y matrices... cuya implementaci´on se optimiza tomando en consideraci´on el entorno en el que se trabaja, tanto en software como en hardware. Este conjunto de instrucciones se conocen como BLAS (basic linear algebra subprograms). Se distinguen tres niveles. El nivel uno est´a formada por operaciones entre vectores, tales como la suma o el producto escalar de dos vectores, de O(n) operaciones, el nivel dos se ocupa de operaciones matriz-vector con O(n2 ) operaciones y el nivel tres son operaciones entre matrices, O(n3 ) operaciones. En m´aquinas con m´ ultiples procesadores estos subprogramas deben adaptarse a dividir la tarea entre los procesadores disponibles de forma ´optima y a buscar algoritmos que soporten este tipo de trabajo5 . 5

Se deben buscar en primer lugar algoritmos que permitan dividir la tarea principal en subtareas equiparables, y de forma que finalicen en tiempos similares puesto que basta con que una de las subtareas se retrase respecto a las dem´ as para que el conjunto de procesadores deba parar a esperar al rezagado con la consiguiente p´erdida de tiempo (y dinero).

40

´ I LECCION

Cap´ıtulo 3. M´etodos directos para sistemas de ecuaciones lineales

Uno de los detalles m´as sencillos que hay que plantear es la estrategia de almacenamiento de las matrices en memoria. Se puede optar por un almacenamiento por filas, como hace C, 

 ⇒

a11 → a12 → a13 → a21 → a22 → a23

r do rra Bo

A=

a11 a12 a13 a21 a22 a23

donde con la notaci´on anterior queremos decir que aij y aij+1 ocupan posiciones consecutivas en memoria. Sin embargo Fortran o Matlab proceden por columnas 

A=

a11 a12 a13 a21 a22 a23





a11 → a21 → a12 → a22 → a13 → a23 .

Seg´ un sea el caso se trata de primar algoritmos que accedan a la matriz por filas o por columnas para que el procesador trabaje con posiciones consecutivas de memoria6 . En esta din´amica, la resoluci´on del sistema triangular seg´ un el algoritmo expuesto en el Ejercicio 3.3 est´a mejor adaptado a la arquitectura de Matlab puesto que todas las operaciones se hacen sobre columnas de la matriz a.

3.1.2.

M´ etodo de Gauss con pivotaje parcial

Para evitar que el m´etodo de Gauss se colapse, es decir, que encuentre en un paso i que el elemento aii es nulo (l´ınea 03 del algoritmo), se introduce la noci´on de pivotaje. La idea es muy sencilla: en el caso de que en el i–´esimo paso el pivote sea nulo, se procede a intercambiar la fila i por una fila k tal que aki 6= 0 para cierto k > i. Si esto no es posible, el sistema no es compatible determinado, es decir, o no tiene soluci´on o tiene infinitas soluciones. Desde un punto de vista pr´actico, el m´etodo de Gauss con pivotaje procede a intercambiar siempre filas de forma que en cada paso |aki | = m´ax |a`i |, `=i,...,n

esto es, el pivote es el mayor posible. Ello dota al sistema de una mayor estabilidad frente a los errores de redondeo. El algoritmo resultante es el siguiente (denotamos por a ↔ b el intercambio de valores de a y b).

6

Cuando un procesador moderno lee algo en memoria, suele cargar a su memoria internar, la memoria cach´e, posiciones adicionales y consecutivas de memoria bajo la convicci´on de que es probable que las requiera en el siguiente paso.

41

´ I LECCION

3.1 M´etodo de Gauss M´ etodo de Gauss con pivotaje parcial 01 02 03

Encontrar k ∈ {i, . . . , n} tal que |aki | = m´ax |a`i | j=`,...,n

for j = i : n aij ↔ akj end bi ↔ bk

r do rra Bo

04 05 08 07 08 09 10 11 12 13 14 15 16

for i = 1 : n − 1

%intercambio filas y termino independiente

for k = i + 1 : n `ki = aki /aii for j = i + 1 : n akj = akj − `ki aij end bk = bk − `ki bi end

end

Ejercicio 3.4 Implementa una funci´on con el m´etodo de Gauss con pivotaje a partir de la funci´on definida en el Ejercicio 3.2. Para este fin la instrucci´on max te puede resultar u´til. Espec´ıficamente, >> [m,i]=max(v)

devuelve en m el mayor valor del vector v y en i su posici´on, esto es, m = v(i). A˜nade tambi´en un control sobre el tama˜no de a(i, i) de forma que si ´este es pr´oximo a cero7 se termine la ejecuci´on y se devuelva un mensaje de error.

(Ayuda. La instrucci´on [m,r]=max(abs(a(i:n,i))) te devolver´a en r la posici´on del m´aximo en el vector columna abs(a(i:n,i)). Por tanto, la fila en la matriz a con el mayor valor en la columna i es i+r-1.)

El intercambio de filas de las l´ıneas 04--08 se puede implementar de varias formas. La primera es simplemente con un bucle que recorra las filas y proceda a intercambiar los valores elemento a elemento. En la segunda forma se hace de forma global mediante aux=a(i,i:n); a(i,i:n)=a(k,i:n); a(k,i:n)=aux;

La tercera forma probablemente ser´a la que resulte m´as extra˜ na pero vuelve a ser natural en Matlab. Basta hacer a([i,k],i:n)=a([k,i],i:n)

F´ıjate que tiene perfecto sentido sint´actico de acuerdo a las reglas de manipulaci´on de vectores y matrices expuestas en la primera parte de esta lecci´on. 7

¿Cu´ando se decide que un n´ umero es cero? En la pr´actica depende de los tama˜ nos del resto de elementos de la matriz.

42

´ I LECCION

3.1.3.

Cap´ıtulo 3. M´etodos directos para sistemas de ecuaciones lineales

M´ etodo de Gauss con pivotaje parcial ficticio

Desde un punto de vista pr´actico no hace falta intercambiar f´ısicamente las filas de la matriz. En lugar de ello se puede utilizar un vector de ´ındices p de forma que p(i) sea la posici´on f´ısica en memoria de la fila i. Inicialmente, las filas est´an sin reordenar, es decir, se empieza declarando

r do rra Bo p=1:n;

Intercambiar las filas i y k es equivalente a intercambiar los valores de p en las posiciones iyk p([i k])=p([k i])

y se procede a hacer ceros en las filas p(i+1),. . . , p(n). El acceso la fila i se consigue con a(p(i),:)

y la b´ usqueda del m´aximo valor para el intercambio de filas con [m,r]=max(abs(a(p(i:n),i)));r=r+i-1;

La fila con el m´aximo elemento en valor absoluto es la p(r). Para la resoluci´on del sistema triangular despejamos igual que en el m´etodo de Gauss, desde la n-´esima inc´ognita a la primera, con 22 23 24 25

x(p(n))=b(p(n))/a(p(n),n); for i=n-1:-1:1 x(p(i))=(b(p(i))-a(p(i),i+1:n)*x(i+1:n))/a(p(i),i); end

Desde un punto de vista estrictamente matem´atico se trata de llevar la matriz a una forma que, si bien no es triangular, una reordenaci´on adecuada de las filas la transforma en triangular. El vector p recoge en qu´e orden se deben despejar las inc´ognitas a la hora de resolver el sistema reducido. En concreto el orden viene dado por p(n), p(n-1),. . . , p(1). En cualquier caso, a(p,:) es una matriz triangular8 . Ejercicio 3.5 Implementa el m´etodo de Gauss con pivotaje parcial ficticio.

Ejercicio 3.6 Las l´ıneas 22–25 proceden a resolver el sistema triangular accediendo a los elementos por filas. Adapta el algoritmo para la resoluci´on de este sistema por columnas, tal como se hizo en el Ejercicio 3.3.

Ejercicio 3.7 Sea A una matriz inversible de tama˜no n × n y A−1 su inversa. Si ai es la columna i−´esima de A−1 , esto es, A−1 = [a1 |a2 | · · · |an ],

8

La importancia de estas t´ecnicas ha decrecido con las u ´ltimas generaciones de ordenadores, donde la manipulaci´on de enormes cantidades de memoria est´a muy optimizada.

43

´ I LECCION

3.2 Descomposiciones matriciales entonces 

r do rra Bo

 0  ..   .    Aai = ei =  1  → i.  .   ..  0

Utilizando alguna de las diferentes versiones del m´etodo de Gauss, implementa el c´alculo de la inversa mediante la resoluci´on de los n sistemas de ecuaciones. Observa que los n comparten la misma matriz de coeficientes.

3.2.

Descomposiciones matriciales

Uno de los aspectos que mejores resultados dio a lo largo del siglo XX, en los albores del ´ An´alisis Num´erica, fue la constataci´on de que numerosos algoritmos del Algebra Lineal, pod´ıan reescribirse como factorizaciones de matrices en producto de otras matrices con ´ caracter´ısticas muy particulares. Este es el caso del algoritmo de Gram-Schmidt, la matriz original escrita como el producto de una ortogonal por una triangular, o el caso que nos ocupa, el m´etodo de Gauss, visto como la b´ usqueda de la factorizaci´on de A como el producto de una matriz triangular inferior por una superior. La utilidad que se concedi´o a este tipo de factorizaciones fue en un primer momento m´as bien te´orica pero r´apidamente se encontr´o aplicaciones pr´acticas y su uso en la actualidad es profuso. Estudiaremos en lo que sigue la factorizaci´on LU y variantes y dejaremos para m´as adelante (Lecci´on IV) otro tipo de factorizaciones.

3.2.1.

Descomposici´ on LU

Supongamos que se dispone de una descomposici´on A = LU

donde L y U son matrices triangulares inferior y superior respectivamente. En este caso, la resoluci´on del sistema lineal Ax = b es equivalente a resolver dos sistemas de ecuaciones triangulares Ly = b, U x = y. el primero triangular superior y el segundo triangular inferior. Puesto que el costo de resoluci´on de cada sistema es O(n2 ) operaciones (total de sumas y productos) obtenemos una ventaja decisiva en la resoluci´on del sistema.

Ejercicio 3.8 Implementa la resoluci´on de un sistema de ecuaciones Lx = b donde L es triangular inferior con 1s en la diagonal.

Si abordamos directamente la resoluci´on de la ecuaci´on A = LU , nos encontramos con un sistema no lineal con n2 + n inc´ognitas (las entradas de L y U ) y n2 ecuaciones (una por cada elemento de a). Por tanto, el sistema resultante no deber´ıa admitir soluci´on 44

´ I LECCION

Cap´ıtulo 3. M´etodos directos para sistemas de ecuaciones lineales

r do rra Bo

u ´nica. Si exigimos que L tenga 1s sobre la diagonal, el n´ umero de inc´ognitas pasa a ser 2 de n y por tanto tenemos ya un sistema cuadrado (aunque no lineal). Se trata entonces de estudiar el siguiente problema: dada una matriz A de tama˜ no n × n, encontrar L y U de la forma     1 u11 u12 · · · u1n  `21 1   u22 · · · u2n      L =  .. U = , .. . . ..  , . .  .   . . .  . `n1 `n2 · · · 1 unn

y tales que A = LU. El c´alculo de esta descomposici´on se puede llevar a cabo sin m´as que exigir que el producto LU sea igual al de A. As´ı empezamos despejando la primera fila de U (que es igual que la de A por ser `11 = 1). Una vez conocida esa fila, se puede despejar la primera columna de L, utilizando que el producto de L por la primera columna de U (que consta de un u ´nico elemento no nulo y ya es conocido del paso anterior) da la primera columna de A. Procedemos sucesivamente de esta forma, construyendo U por filas y L por columnas. Descomposici´ on LU (M´ etodo de Doolittle) 01 02

for k = 1 : n for j = k : n

ukj = akj −

03

k−1 X

`kp upj

p=1

04 05 06

end `kk = 1 for i = k + 1:n k−1   X `ip upk /ukk `ik = aik −

07

p=1

08 09

end

end

El n´ umero de operaciones del algoritmo resulta ser igual al del m´etodo de Gauss, con lo cual no hemos conseguido una ventaja significativa. Sin embargo, disponer de esta descomposici´on es especialmente u ´til si se requiere resolver varios sistemas de ecuaciones lineales con la misma matriz pero con t´erminos independientes diferentes. Las operaciones que conllevan un mayor coste son las correspondientes al c´alculo de las matrices L y U , pero u ´nicamente hay que realizar esta descomposici´on una vez para posteriormente resolver en cada caso dos sistemas triangulares. Ejercicio 3.9 Implementar la descomposici´on LU en Matlab mediante una funci´on cuya entrada sea una matriz cuadrada y su salida sean las matrices L y U correspondientes. (Ayuda: la funci´on por tanto devuelve dos valores.)

45

´ I LECCION

3.2 Descomposiciones matriciales

r do rra Bo

Al observar el algoritmo del m´etodo, las operaciones recuerdan a las efectuadas por el m´etodo de Gauss. Esto no es tan sorprendente cuando se analizan con detenimiento los calculados realizados. Se puede ver entonces que en el c´alculo de la descomposici´on LU se est´an haciendo exactamente las mismas operaciones que al aplicar el m´etodo de Gauss. En efecto, definamos ( (1) aij = aij i, j = 1, . . . , n (k+1)

aij

(k)

(k)

= aij − `ik akj ,

k ≥ 1,

1 ≤ i, j ≤ n − k

donde `ki viene dada por el algoritmo de Doolitle (l´ınea 07). Entonces, de acuerdo con el algoritmo de la factorizaci´on LU , los elementos de la primera fila de U y de la primera columna de L vienen dados por (1)

(1)

u1j = a1j ,

`i1 =

ai1

(1)

.

a11

En el siguiente paso, se observa que

(1)

(1)

(1)

(1)

(2)

u2j = a2j − `21 u1j = a2j − `21 a1j = a2j `i2 =

(2)

a − `i1 a ai2 − `i1 u12 a = i2 (2) 12 = i2 . (2) u22 a22 a22

Reiterando el mismo razonamiento concluimos que

(j)

uij =

(i) aij ,

i ≤ j,

`ij =

aij

(j)

,

i > j.

ajj

Por tanto U es de hecho la matriz triangular que queda al aplicar el m´etodo de Gauss mientras que L est´a formada por los elementos que se han utilizado para hacer ceros en el proceso. Esto es, el elemento i, j de L, denotado por `ij , coincide con la constante `ij calculado en la l´ınea 03 del m´etodo de Gauss y por tanto no hay una contradicci´on de notaciones. En particular, la propiedad anterior propone una forma alternativa de calcular la descomposici´on LU de una matriz es la siguiente modificaci´on del programa del Ejercicio 3.1: 11 12 13 14 15 16 17

for i=1:n-1} a(i,i+1:n)=0; %hacemos cero la columna i for k=i+1:n} l(k,i)=a(k,i)/a(i,i); a(k,i+1:n)=a(k,i+1:n)-l(k,i)*a(i,i+1:n); end end

La matriz U estar´ıa entonces almacenada en a.

Ejercicio 3.10 Una forma compacta de devolver la descomposici´on LU es insertar L en la parte triangular inferior de a. De esta forma, tras aplicar el m´etodo, a tiene en la parte superior la matriz U , mientras que por debajo de la diagonal encontramos L (exceptuando su diagonal de 1s). Implementa esta modificaci´on. 46

´ I LECCION

3.2.2.

Cap´ıtulo 3. M´etodos directos para sistemas de ecuaciones lineales

Casos particulares

M´ etodo de Cholesky En una gran variedad de problemas pr´acticos aparecen matrices sim´etricas definidas positivas. Este tipo de matrices puede descomponerse en la forma

r do rra Bo A = LL>

donde



  L= 

`11 `21 `22 .. .. . . . . . `n1 `n2 · · · `nn



  . 

Gracias a la simetr´ıa de la matriz, tanto el n´ umero de operaciones como de posiciones de memoria requeridos pueden reducirse a la mitad. El algoritmo resultante es conocido como el m´etodo de Cholesky. M´ etodo de Cholesky 01

02

for k = 1:n v u k−1 u X `2kr `kk = takk − r=1

for j = k + 1:n k−1   X `jr `kr /`kk `jk = ajk −

03 04

r=1

05 06

end

end

Ejercicio 3.11 Implementa una funci´on que tenga como entrada una matriz A y devuelva la matriz L correspondiente. Debe avisar si la descomposici´on no ha podido llevarse a cabo. Implementa tambi´en una segunda funci´on que tenga como entradas la matriz L triangular y un t´ermino independiente b y que devuelva la soluci´on del sistema (LL> )x = b.

Para ello se requiere la resoluci´on de los sistemas triangulares L> x = y.

Ly = b,

LU con permutaci´ on

El m´etodo de Gauss con pivotaje parcial es equivalente a la decomposici´on P A = LU 47

´ I LECCION

3.2 Descomposiciones matriciales

donde P es el resultado de permutar las filas (o columnas) de la identidad. Alternativamente, equivale a una descomposici´on de la forma b A = LU

r do rra Bo b = P −1 L, de forma que L b es una permutaci´on de la matriz triangular inferior9 . donde L La siguiente subrutina devuelve esa descomposici´on.

01 02 03 04 05 06 07 08 09 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25

% % % % % % %

LUPERMUTACION

[L,U]=LUPERMUTACION(A)

devuelve U triangular superior, L permutacion por filas de una matriz triangular inferior con 1s en la diagonal de forma que A=L*U

function [l,u]= LUPermutacion(a) n=length(a); p=1:n;

for i=1:n-1 [maximo,r]=max(abs(a(p(i:n),i)));r=r+i-1; p([i r])=p([r i]); for k=i+1:n l(p(k),i)=a(p(k),i)/a(p(i),i); a(p(k),i:n)=a(p(k),i:n)-l(p(k),i)*a(p(i),i:n); end end for i=1:n l(p(i),i)=1; end u=a(p,:); return

3.2.3.

Comandos correspondientes en Matlab

Todas las factorizaciones vistas con anterioridad est´an, por supuesto, implementadas en Matlab. Algunos de los comandos relacionados son 9

Esto es, es el resultado de reordenar las filas de L.

48

´ I LECCION

Cap´ıtulo 3. M´etodos directos para sistemas de ecuaciones lineales

[l,u]=lu(a) devuelve u triangular superior, l permutaci´on de una triangular inferior con 1s en la diagonal de forma que a=l*u. [l,u,p]=lu(a) devuelve u triangular superior, l triangular inferior con 1s en la diagonal y p matriz de permutaci´on de forma que p*a=l*u.

r do rra Bo

r=chol(a) devuelve r triangular superior de forma que a=r’*r. Observa que con las notaciones introducidas r es precisamente la traspuesta de la matriz L, expuesta en nuestro algoritmo. El comando asume que la matriz es sim´etrica por lo que s´olo trabaja con la parte superior de la matriz.

Otra descomposici´on habitual10 es la denominada QR que devuelve Q ortogonal (es decir, Q> Q = In ) y R triangular superior de forma que A = QR. El comando encargado de esta tarea es qr. Con estas instrucciones la soluci´on de un sistema utilizando la descomposici´on LU se ejecuta con las siguientes l´ıneas [l,u]=lu(a); x=u\(l\b);

La colocaci´on de los par´entesis es esencial. Con u\l\b se calcula (u−1 l)−1 b que obviamente no tiene nada que ver con la soluci´on del sistema. No hay que preocuparse por el hecho de que las matrices sean triangulares (o permutaci´on de una triangular). Matlab, y en concreto la instrucci´on \ detecta esto y resolver´a el sistema por sustituci´on progresiva (o regresiva), sin intentar realizar la eliminaci´on gaussiana.

Nota hist´ orica11

Ideas similares a la eliminaci´on gaussiana pueden encontrarse muchos siglos atr´as, con referencias que se remontan a las matem´aticas babil´onicas y chinas. Carl Friedreich Gauss introdujo el m´etodo que lleva su nombre entorno a 1800 cuando trataba de resolver un problema de ajuste por m´ınimos cuadrados relacionado con el c´alculo de la ´orbita del asteroide Palas. Parece ser que Joseph Louis Lagrange hab´ıa utilizado ideas similares 50 a˜ nos antes para dilucidar si una forma cuadr´atica (hoy dir´ıamos matriz) era definida positiva. El matem´atico alem´an Carl Gustav Jacob Jacobi extendi´o la idea de la eliminaci´on gaussiana a matrices arbitrarias. Es rese˜ nable que la noci´on de matriz tal como la conocemos ahora era desconocida para Gauss y Lagrange. El concepto de matriz, y el ´algebra asociada (esto es, las operaciones) habr´ıan de esperar a los trabajos de James J. Sylvester (que en 1848 introdujo el t´ermino matriz) y de Arthur Cayley (que siete a˜ nos despu´es defini´o el producto matricial identific´andolo con el c´alculo de la composici´on de aplicaciones lineales y defini´o la inversa de una matriz). Importantes fueron tambi´en las contribuciones del f´ısico Hermann 10

Veremos dos algoritmos para obtener esta descomposici´on en la Lecci´on IV. Aunque para la resoluci´on de sistemas de ecuaciones lineales la descomposici´on QR es m´as estable num´ericamente que la LU, se suele optar por esta u ´ltima por tener un menor coste computacional (aproximadamente la mitad). 11 Las principales referencias utilizadas para esta nota han sido “Very Early Days of Matrix Computations”, Beresford Parlett en SIAM News, 3, no 9; “Matrix Algorithms”, G.W. Stewart; “Computer solutions of large system of equations”, G. Merant y “An introduction to Numerical Analysis”, E. S¨ uli y D. Mayers. Estas referencias est´ an completamente detalladas en la bibliograf´ıa.

49

´ I LECCION

3.2 Descomposiciones matriciales

r do rra Bo

Grassmann (introdujo la primera ´algebra vectorial no conmutativa, basada en el producto vectorial de dos vectores; consider´o tambi´en el producto de un vector fila por un vector columna que daba lugar a una matriz de rango uno), Willard Gibbs y Paul A. Dirac. La equivalencia entre la descomposici´on LU y la eliminaci´on gaussiana parece que fue probada por primera vez por Paul S. Dwyer en 1944. Curiosamente, la descomposici´on de Cholesky es anterior. Publicado p´ostumamente en 1924 en una revista de Geodesia (Andr´e-Louis Cholesky muri´o en 1918). El trabajo original trataba sobre la resoluci´on de un problema de ajuste por m´ınimos cuadrados y pas´o desapercibido hasta que fue rescatado por John Todd a finales de los a˜ nos 1940. Los primeros an´alisis sobre la estabilidad num´erica de la eliminaci´on gaussiana, es decir la viabilidad de su programaci´on, se remontan a los trabajos de Harold Hotelling, Alan Turing12 , John von Neumann y Herman Heine Goldstine. Los resultados iniciales eran descorazonadores. Harold Hotelling prob´o en torno a 1940 que el error de redondeo podr´ıa crecer como 4n donde n era el orden de la matriz. Este resultado colocaba al m´etodo de Gauss como un m´etodo inviable para la resoluci´on de grandes sistemas lineales. Turing lleg´o a resultados similares de manera informal. El an´alisis de Neumann y Goldstine ya probaba que el m´etodo era estable para matrices definidas positivas13 . James H. Wilkinson, reconocido universalmente como el padre del an´alisis moderno de estabilidad (frente a los errores de redondeo), extendi´o el an´alisis a matrices generales y mostr´o que el pivotaje mejoraba enormemente la estabilidad del m´etodo. Lo m´as curioso es que el an´alisis inicial estaba enfocado m´as hacia el c´alculo de la inversa de la matriz que al m´etodo de Gauss. Como curiosidad final, Cleve Moler, programador original de Matlab, cita14 a Wilkinson y Todd entre las personas que tuvieron una gran influencia en su formaci´on y por ende en los or´ıgenes de Matlab.

12

La vida de Alan Turing es una de las m´as tr´agicas en historia de las matem´aticas. Dotado de una inteligencia precoz, realiz´ o contribuciones importantes en l´ogica y computaci´on. Trabaj´o durante la segunda guerra mundial en Bletchley Park en el descifrado de los c´odigos alemanes encriptados con la m´aquina Enigma mediante la utilizaci´ on del primer ordenador electr´onico en el mundo (Colossus). El papel que este trabajo an´ onimo tuvo en la victoria aliada, los alemanes siempre estuvieron seguros de que su c´odigo era indescifrable, s´ olo ha empezado a reconocerse en fechas recientes. La presi´on y aislamiento a la que Turing fue sometido por su homosexualidad, llegando incluso a ser detenido por ello, le llev´o al suicidio en 1954 despu´es de haberse sometido a un tratamiento con bromuro para curarle de su enfermedad. 13 En los primeros a˜ nos se sugiri´ o incluso resoluci´on de un sistema Ax = b mediante las ecuaciones normales A> Ax = A> b (A> A es sim´etrica y definida positiva). 14 http://www.mathworks.com/company/newsletters/news notes/clevescorner/dec04.html

50

r do rra Bo Lecci´on II

Programaci´on avanzada en Matlab. M´etodos iterativos para sistemas de ecuaciones lineales

51

r do rra Bo

r do rra Bo

Introducci´ on

Homer: Marge? Since I’m not talking to Lisa, would you please ask her to pass me the syrup? Marge: Dear, please pass your father the syrup, Lisa. Lisa: Bart, tell Dad I will only pass the syrup if it won’t be used on any meat product. Bart: You dunkin’ your sausages in that syrup homeboy? Homer: Marge, tell Bart I just want to drink a nice glass of syrup like I do every morning. Marge: Tell him yourself, you’re ignoring Lisa, not Bart. Homer: Bart, thank your mother for pointing that out. Marge: Homer, you’re not not-talking to me and secondly I heard what you said. Homer: Lisa, tell your mother to get off my case. Bart: Uhhh, dad, Lisa’s the one you’re not talking to. Homer: Bart, go to your room. The Simpsons, Episodio 5, temporada 5, Lisa the Vegetarian

En el primer apartado entraremos en aspectos m´as avanzados en el tratamiento de vectores y matrices en Matlab, haciendo hincapi´e especial en la manipulaci´on de matrices sparse. Veremos tambi´en c´omo se pueden implementar funciones donde el n´ umero de argumentos de entrada y salida son variables. En la parte matem´atica, tocaremos la teor´ıa b´asica de m´etodos iterativos para sistemas de ecuaciones lineales. Empezaremos con los m´etodos cl´asicos: Jacobi, Gauss–Seidel y relajaci´on de Young, para pasar luego a m´etodos m´as modernos y elaborados: el m´etodo del Gradiente y especialmente, el m´etodo del Gradiente Conjugado. En esta lecci´on nos permitiremos hacer algo de Matem´aticas. Animamos a que el lector no se asuste por ello y a que trate de entender los enunciados y las demostraciones que se ´ ofrecen. Para ello se asumen unos conocimientos m´ınimos en Algebra Lineal.

53

r do rra Bo

r do rra Bo

Cap´ıtulo 4

Matlab: programaci´ on avanzada 4.1.

Retorno a las matrices

A estas alturas el lector ya deber´ıa estar convencido sobre las capacidades de Matlab en lo que se refiere al manejo de enormes cantidades de memoria. En esta secci´on expondremos algunos comandos adicionales y entraremos con cierto detalle en la manipulaci´on de matrices sparse1 .

4.1.1.

Acceso a partes estructuradas de una matriz

En ocasiones es importante tomar partes precisas de una matriz que no son necesariamente partes de filas, columnas o simplemente submatrices (estas acciones ya se trataron en la primera lecci´on). Para este fin nos pueden servir las siguientes instrucciones diag

triu

tril

La primera toma la diagonal de una matriz mientras que la segunda y tercera toman la parte triangular superior (upper) e inferior (lower) respectivamente. Adem´as estos comandos son algo m´as flexibles de lo que pueda parecer a simple vista como veremos a continuaci´on. Empecemos introduciendo una matriz >> a=[11 12 13; 21 22 23; 31 32 33];

El resultado de los siguientes comandos es, a la luz de lo anterior, esperable >> diag(a) ans = 11 22 33

1

Aceptaremos este anglicismo en lo que sigue. En ocasiones este vocablo se traduce por matrices huecas o matrices dispersas.

55

´ II LECCION

4.1 Retorno a las matrices

>> triu(a) ans = 12 22 0

13 23 33

r do rra Bo

11 0 0

>> tril(a) ans = 11 21 31

0 22 32

0 0 33

El usuario puede especificar qu´e diagonal se escoge, o a partir de qu´e diagonal se toma la matriz triangular. La diagonal principal es la cero y las subdiagonales inferiores (respectivamente superiores) est´an numeradas consecutivamente con n´ umeros enteros negativos (respectivamente positivos). El siguiente ejemplo ilustra estas caracter´ısticas. >> diag(a,-1) ans =

21 32

>> tril(a,-1) ans =

0 21 31

0 0 32

0 0 0

>> triu(a,0) ans =

11 0 0

12 22 0

13 23 33

Ejercicio 4.1 Programa una funci´on que dada una matriz a devuelva un vector d con los elementos de la diagonal, una matriz triangular superior u con todos los elementos de a situados 56

´ II LECCION

Cap´ıtulo 4. Matlab: programaci´on avanzada

encima de la diagonal superior y l una matriz triangular inferior con todas las entradas de debajo de la diagonal principal. Ejercicio 4.2 ¿Qu´e sucede si aplicamos los comandos anteriores a matrices rectangulares?.

r do rra Bo

Con diag podemos tambi´en construir a partir de un vector una matriz diagonal >> diag([1 2])

% es lo mismo que diag([1 2],0)

ans =

1 0

0 2

>> diag([1 2],1) ans =

0 0 0

1 0 0

0 2 0

Ejercicio 4.3 ¿C´omo utilizar´ıas el comando diag para generar una matriz con la diagonal de una dada?. Nota. El comando blkdiag permite construir matrices diagonales por bloques: >> blkdiag(1,[1 2; 3 4], 5) ans=

1 0 0 0

0 1 3 0

0 2 4 0

0 0 0 5



Trasposici´ on de matrices

Dada una matriz A, la matriz traspuesta A> es la matriz resultante de intercambiar las filas con las columnas de A. Esto es, las filas de A pasan a ser las columnas de A> . Esta operaci´on se denota en Matlab con “ ’ ” : >> a=[1 2 3; 0 2 4]; >> a’ ans = 57

´ II LECCION

4.1 Retorno a las matrices

1 2 3

0 2 4

r do rra Bo

Obviamente, tambi´en se aplica sobre vectores:

>> b=[1;2;3]; % vector COLUMNA con tres elementos >> b’ % vemos ahora un vector FILA ans =

1

2

3

De nuevo nos encontramos con esta propiedad sobre la que ya hemos incidido: Matlab distingue entre vectores filas y columnas, y esta diferencia se hace especialmente palpable (y en ocasiones molesta) a la hora de realizar operaciones como productos matriz-vector.

Nota. En Matlab existe tambi´en el operador “.’”. Sobre matrices reales funciona exactamente igual que el comando anterior, pero no as´ı sobre n´ umeros complejos. Adem´as de trasponer, “’”, conjuga todas las entradas. Es decir, cambia el signo a la parte imaginaria de cada elemento. Matem´aticamente hablando, ´este es el operador de trasposici´on o conjugaci´on, denotado habitualmente en matem´aticas con “A∗ ”. Por contra, “.’” se limita a intercambiar filas por columnas en la matriz: >> clear i % i es ahora la unidad imaginaria >> a=[i 1-2i; 1 0.3+4i]; >> a.’ ans =

0 + 1.0000i 1.0000 - 2.0000i

1.0000 0.3000 + 4.0000i

>> a’ ans =

0 - 1.0000i 1.0000 + 2.0000i

1.0000 0.3000 - 4.0000i

 Dada una matriz a, si ejecutamos a(:), obtenemos el vector columna que se construye concatenando las columnas de a. T´ecnicamente hablando, nos est´a mostrando la matriz tal como se guarda en memoria. Por ejemplo, 58

´ II LECCION

Cap´ıtulo 4. Matlab: programaci´on avanzada

>> a=[1 2 3; 0 2 4]; >> a(:) ans =

r do rra Bo

1 0 2 2 3 4

>> a=a’; %trasponemos a >> a(:) ans =

1 2 3 0 2 4

Esto puede utilizarse para hacer un par de trucos:

En ocasiones la entrada de una funci´on es un vector, sin importar si ´este es fila o columna. La instrucci´on

>> b=b(:);

har´a de b un vector columna, sea cual sea su formato inicial. Si lo que se desea es un vector fila, basta con trasponer >> b=b(:)’; % b=b(:).’ mejor por si b es complejo

Se puede utilizar para introducir las entradas de una matriz por columnas. A modo de ejemplo, >> a=zeros(4,3); >> a(:)=[1 2 3 4 5 6 7 8 9 10 11 12] a =

59

´ II LECCION

4.1 Retorno a las matrices 1 2 3 4

5 6 7 8

9 10 11 12

r do rra Bo

>> a2=zeros(2,6); >> a2(:)=a(:) a2=

1 2

3 4

5 6

7 8

9 10

11 12

Nota. El comando reshape permite modificar las dimensiones de una matriz (o array en general). Es m´as flexible que el comando “:”. 

4.1.2.

M´ as operaciones sobre matrices

Hasta ahora las operaciones matriciales que han centrado nuestra atenci´on son las fundamentales: suma y producto. En Matlab est´an tambi´en implementadas otras operaciones ´ comunes en el Algebra Lineal. Entre todas ellas destacamos dot: Calcula el producto escalar de dos vectores: >> dot([1 2 3],[4 5 6]) ans =

32

Devuelve el produto 1 · 4 + 2 · 5 + 3 · 6 = 32. Este comando no distingue entre vectores filas y columnas, y es aplicable siempre que tengan la misma longitud. La funci´on se puede aplicar a matrices bien por columnas, ´esta es la forma est´andar2 , o por filas. >> a=[1 2 3; 4 5 6]; a2=[1 1 1; 1 1 1]; >> dot(a,a2) % producto por columnas ans =

5

2

7

9

Recuerda la predilecci´ on de Matlab por las columnas.

60

´ II LECCION

Cap´ıtulo 4. Matlab: programaci´on avanzada

>> dot(a,a2,2) % producto por filas ans =

r do rra Bo

6 15

sum: calcula la suma de las entradas un vector. Es aplicable tambi´en a matrices, en el sentido del comando anterior >> v=[1 2 3]; a=[1 2 3; 4 5 6]; >> sum(v) ans =

6

>> sum(a)

% suma por columnas

ans =

5

7

>> sum(a,2)

9

% suma por filas

ans =

6 15

prod: Como sum pero con el producto.

max: Calcula el m´aximo en un vector. Puede devolver su posici´on en el vector. Aplicado sobre matrices funciona de la misma forma que dot o sum. Esto es, devuelve el m´aximo de cada columna por defecto, o de cada fila si as´ı se le indica >> v=[-2 -5 -3]; a=[2 3 8; -4 2 9]; >> max(v) ans=

-2

>> [p,m]=max(abs(v)); [p,m]

61

´ II LECCION

4.1 Retorno a las matrices ans = 5

2

>> max(a)

r do rra Bo ans =

2

3

9

>> max(a,[],2)

% busqueda por filas

ans =

8 9 >> [m,p]=max(a,[],2); p % posicion del maximo ans=

1 1

La raz´on por la que se utiliza [] en la l´ınea anterior es que esta instrucci´on tambi´en se puede utilizar para comparar dos arrays del mismo tama˜ no >> a1=[3 1 2; 5 3 2]; a2=[4 2 1; 1 2 3]; >> max(a1,a2) ans =

4 5

2 3

2 3

Al insertar el vac´ıo indicamos a Matlab que no existe un segundo vector y que debe proceder a buscar el m´aximo de a en su segunda dimensi´on, esto es, el m´aximo por filas.

min: Calcula el m´ınimo procediendo exactamente igual que max.

norm: norma de una matriz o vector. Se puede escoger entre varias normas.

>> v=[1 2 3];a=[1 2; 3 4]; >> [norm(v) norm(v,1) norm(v,inf)] % norma 2, 1 e infinito de v ans =

62

´ II LECCION

Cap´ıtulo 4. Matlab: programaci´on avanzada 3.7417

6.0000

3.0000

>> [norm(a) norm(a,1) norm(a,inf)] % normas matriciales ans =

r do rra Bo 5.4650

6.0000

7.0000

En la Secci´on 5.2.3 comentaremos brevemente la definici´on de estas normas.

rank: rango num´erico de una matriz. Esto es, el n´ umero m´aximo de filas o columnas 3 linealmente independientes .

cond: Calcula norm(a)*norm(inv(a)), el condicionamiento de una matriz4 . El condicionamiento da una medida de la sensibilidad del sistema a perturbaciones en el t´ermino independiente.

rcond: estimador del inverso del condicionamiento de una matriz. Es sensiblemente m´as econ´omico de calcular que cond.

Nota. Cuando el comando dot se aplica a dos vectores complejos, procede siempre a conjugar el primer vector. Es decir, matem´aticamente n X

dot(u, v)

ui v i .

i=1

As´ı,

>> u=[1+i 2+2i]; v=[2 1]; >> dot(u,v) ans =

4.0000 - 4.0000i

>> dot(v,u) ans =

4.0000 + 4.0000i



Ejercicio 4.4 ¿C´omo sumar´ıas los elementos de una matriz?. ¿C´omo encontrar´ıas el m´ınimo y el m´aximo?. ¿Y su posici´on? 3

Una matriz tiene, en general, rango m´ aximo por los errores de precisi´on de la m´aquina. Este comando hace una estimaci´ on del rango, eliminando este factor. 4 En realidad no construye la inversa de la matriz por ser costoso.

63

´ II LECCION

4.1 Retorno a las matrices

4.1.3.

Matrices sparse

r do rra Bo

Las matrices sparse son una importante clase de matrices que surge en diferentes a´mbitos del An´alisis Num´erico y de las Matem´aticas y ciencias en general (elementos finitos, teor´ıa de grafos,...). En la Figura 4.1 se puede ver un ejemplo de una matriz sparse sim´etrica donde los puntos indican las entradas diferentes de cero. Desde una ´optica puramente computacional hace falta desarrollar sistemas de almacenamiento especiales dado que la inmensa mayor´ıa de las entradas no deben ser almacenadas porque son nulas.

Figura 4.1: Diagrama de un matriz sparse 400 × 400 con 2690 elementos no nulos. Matlab provee de forma muy sencilla ese almacenamiento. Con >>a=sparse(100,100); b=sparse(100,1);

declaramos a como una matriz sparse 100×100 y un vector columna b de 100 elementos. Todas las entradas son inicialmente ceros, pero se guarda la estructura b´asica para introducir los elementos no nulos >> a=sparse(100,100) a =

All zero sparse: 100-by-100

>> a(4,4)=1; a(8,9)=-4; a(80,45)=-1; a(99,100)=4; >> a a =

64

´ II LECCION

Cap´ıtulo 4. Matlab: programaci´on avanzada

(4,4) (8,9) (80,45) (99,100)

1 -4 -1 4

r do rra Bo

Para transformar una matriz llena (convencional) en una matriz sparse podemos utilizar tambi´en este comando >> a=diag([1 2 3 4 5]); >> a=sparse(a) a =

(1,1) (2,2) (3,3) (4,4) (5,5)

1 2 3 4 5

Con full realizamos la operaci´on inversa: transforma una matriz sparse en una matriz llena, >> a=full(a) a =

1 0 0 0 0

0 2 0 0 0

0 0 3 0 0

0 0 0 4 0

0 0 0 0 5

La instrucci´on spalloc tiene un funcionamiento muy similar a sparse. Es u ´til si se sabe el n´ umero de elementos no nulos que tendr´a dicha matriz. Concretamente >> a=spalloc(8,7,12)

declara una matriz 8 × 7 con a lo sumo 12 elementos no nulos. Al informar de cu´antos elementos no nulos se esperan Matlab hace una gesti´on m´as eficiente de la memoria. El comando nnz (Non zeros) nos informa del n´ umero de elementos no nulos de una matriz, mientras que su esquema (pattern), como el que aparece en la Figura 4.1, se obtiene con spy: >> a=sparse(10,10); >> a(1,4)=1; a(2,8)=-4; a(3,9)=1; a(7,8)=5; >> nnz(a) ans=

65

´ II LECCION

4.2 Argumentos de funciones 4 >> spy(a)

r do rra Bo

La gr´afica se despliega en una ventana separada. Todas las operaciones que hemos visto est´an adaptadas al nuevo entorno. As´ı, los operadores :

triu

tril

diag

devuelven vectores/matrices sparse. Las operaciones *

+

.*

dot



est´an asimismo optimizadas. El problema de generar c´odigo eficiente no es tan simple como pudiera parecer. Por ejemplo, si se aplica la funci´on dot a dos vectores sparse es preciso saber antes qu´e entradas hay que multiplicar. De otra forma podr´ıamos estar dedicando un alto porcentaje de nuestro esfuerzo en simplemente calcular productos por cero. Afortunadamente, Matlab hace ese trabajo por nosotros. Por otro lado, aparecen una nueva serie de comandos, que devuelven matrices sparse, entre los que merece la pena destacar spdiags maneja las diagonales de una matriz de forma an´aloga a diag;

speye devuelve una matriz diagonal con unos, o similar (an´aloga a eye);

spones matriz de 1s, similar a ones;

sprand, sprandn construyen una matriz sparse con entradas aleatorias (similar a rand);

Ejercicio 4.5 Con la ayuda de Matlab averigua la sintaxis concreta de los comandos anteriores y comprueba con alg´un ejemplo c´omo funcionan.

4.2.

Argumentos de funciones

Veremos a continuaci´on c´omo se pueden programar funciones en las que tanto el n´ umero de argumentos de entrada como de salida sean variables. Esta caracter´ıstica dota de una mayor flexibilidad a la programaci´on en Matlab. Los comandos esenciales que precisamos son varargin

nargin

varargout

nargout

La instrucciones nargin y nargout informan respectivamente sobre el n´ umero de variables de entrada y el n´ umero de variables de salida (number of input arguments y number of output arguments). Una funci´on puede aceptar una serie de argumentos fijos, al estilo de las funciones que programamos en la lecci´on anterior, y un conjunto de argumentos opcionales, que pueden 66

´ II LECCION

Cap´ıtulo 4. Matlab: programaci´on avanzada

ser o no especificados por el usuario. Para su acceso se utilizan respectivamente varargin (variable input argument) y varargout (variable output argument) mediante llaves ({})5 . Mostramos a continuaci´on un ejemplo de utilizaci´on conjunta de estas nuevas instrucciones. En la cabecera se informa de qu´e hace la funci´on, dependiendo de los argumentos de entrada y salida.

r do rra Bo 01 02 03 04 05 06 07 08 09 10 11 12 13 14 15 16 17 18 19 20 21 22 23

% DESCOMPOSICIONLU % % [L,U] = DESCOMPOSICIONLU(A) % Devuelve U triang superior, L permutacion de una % triang inferior con 1s en la diagonal tal que A=LU % % [L,U,X] = DESCOMPOSICIONLU(A,B) % Devuelve U triang superior, L permutacion de una % triang. inferior con 1s en la diagonal tal % que A=LU y la solucion del sistema AX=B function varargout=DescomposicionLU(a,varargin) [l,u]=lu(a);

% descomposicion LU

if nargin==1 & nargout==2 varargout{1}=l; varargout{2}=u; elseif nargin==2 & nargout==3 b=varargin{1}; % leemos el primer argumento opcional... varargout{1}=l; varargout{2}=u; varargout{3}=u\(l\b); % solucion del sistema end

Como puede comprobarse, la funci´on precisa de un argumento obligatorio, la matriz a, uno opcional, el t´ermino independiente, y devuelve dos o tres argumentos seg´ un se requiera. Observa los resultados que se han obtenido para varios ejemplos: >> a=[1 3; 2 4]; >> [l,u]=DescomposicionLU(a) l =

0.5000 1.0000

1.0000 0

u =

5

Las variables varargin y varargout son de un tipo especial denominado cell array. En la Lecci´on IV estudiaremos su funcionamiento con m´ as detalle.

67

´ II LECCION

4.2 Argumentos de funciones 2 0

4 1

>> [l,u,x]=DescomposicionLU(a,[1 2].’)

r do rra Bo

l =

0.5000 1.0000

1.0000 0

u =

2 0

4 1

x =

1 0

>> [l,u]=DescomposicionLU(a,[1 2]) %falta un arg. de salida ??? Error using ==> DescomposicionLU Too many output arguments.

>> [l,u,x]=DescomposicionLU(a) %faltan arg. de entrada ??? Error using ==> DescomposicionLU Too many output arguments.

Ejercicio 4.6 A partir de la funci´on anterior implementa una funci´on que opere seg´un la “siguiente cabecera” % % % % % % % % % % % % % % %

DESCOMPOSICIONLU2 R

= DESCOMPOSICIONLU2(A) Si A es simetrica definida positiva devuelve R triang superior tal que A=R’R [R,X] = DESCOMPOSICIONLU2(A,B) Si A es simetrica definida positiva devuelve R triang superior tal que A=R’R y la solucion del sistema AX=B [L,U] = DESCOMPOSICIONLU2(A) Devuelve U triang superior, L permutacion de una triang. inferior con 1s en la diagonal tal que A=LU [L,U,X]= DESCOMPOSICIONLU2(A,B) Devuelve U triang superior, L permutacion de 68

´ II LECCION % %

Cap´ıtulo 4. Matlab: programaci´on avanzada una triang. inferior con 1s en la diagonal tal que A=LU y la solucion del sistema AX=B

Nota: Realizar la comparaci´on A’==A para testar si la matriz es sim´etrica. ¿Qu´e devuelve esta comparaci´on? ¿C´omo se puede utilizar para comprobar si efectivamente la matriz es sim´etrica? ¿Y para ver que es definida positiva?.

r do rra Bo 69

´ II LECCION

4.2 Argumentos de funciones

r do rra Bo 70

r do rra Bo

Cap´ıtulo 5

Matrices sparse en Matem´ aticas. M´ etodos iterativos para sistemas de ecuaciones lineales 5.1.

M´ etodo de Gauss para matrices sparse

Esta secci´on se centra en el estudio del m´etodo de Gauss para matrices sparse. Mostraremos los problemas que presenta la aplicaci´on de este algoritmo a este tipo de matrices, especialmente el efecto relleno y algunas estrategias de reordenamiento que mitigan estos efectos adversos. Sirve asimismo para ahondar en la problem´atica de los m´etodos directos y allanar y fundamentar los m´etodos iterativos que se tratan en las siguientes secciones. Recordemos que en Matlab la resoluci´on de sistemas de ecuaciones utilizando >> x=a\b;

se basa en el m´etodo de Gauss (o alguna de sus variantes). Puede plantearse la cuesti´on de si es adecuado utilizar “\” para matrices con formas especiales como por ejemplo matrices triangulares o permutaciones de ´estas, para las que la eliminaci´on gaussiana no es necesaria puesto que las variables se pueden despejar de forma progresiva. Afortunadamente Matlab detecta estas estructuras b´asicas y resuelve de una manera ´optima el sistema. Si se consulta la ayuda para este comando se puede leer que se reconoce si una matriz es, por ejemplo, sparse o llena, sim´etrica o no sim´etrica, triangular o permutaci´on de ´esta, bandeada (los elementos concentrados en torno a la diagonal), de Hessenberg1 (con todos los elementos por debajo de la subdiagonal principal nulos), etc., y aplica el m´etodo directo m´as conveniente en cada caso. Testar si una matriz pertenece a uno de estos tipos se puede realizar en un n´ umero de operaciones despreciable respecto a las del m´etodo de Gauss. Hemos visto al final de la Lecci´on I que el m´etodo de Gauss es matem´aticamente equivalente a calcular dos matrices L y U triangular inferior y superior respectivamente con 1s en la diagonal de L de forma que A = LU. 1

Ver Lecci´ on IV

71

´ II LECCION

5.1 M´etodo de Gauss para matrices sparse

Si se dispone de esta descomposici´on, la resoluci´on del sistema de ecuaciones se reduce a la resoluci´on de dos sistemas triangulares, Ax = b,

Ly = b,

U x = y,

o en c´odigo de Matlab2

r do rra Bo [l,u]=lu(a); x=u\(l\b);

Una caracter´ıstica muy habitual del m´etodo de Gauss para matrices sparse es el efecto relleno (en ingl´es fill in), esto es, la inserci´on de nuevos elementos en el proceso. Por ejemplo, tras un u ´nico paso del m´etodo de Gauss     x x x x x x x x x x x x  x x   x x x x x       x    x x x x x x  ∼   x   x x x x x x       x   x x x x x x  x x x x x x x

y la matriz es ahora llena. Sin llegar a esos extremos, es habitual que las necesidades de memoria se multipliquen al aplicar la eliminaci´on gaussiana. En la descomposici´on LU esto se refleja en un incremento en el n´ umero de entradas no nulas de la matriz con los problemas que ello lleva consigo (mayores requerimientos de memoria, mayor costo computacional,...). Vamos a ver como podemos reducir este molesto comportamiento con un reordenamiento adecuado de filas (ecuaciones) y columnas (inc´ognitas). Dado que en aplicaciones pr´acticas las matrices sim´etricas son muy comunes3 nos restringiremos en lo que sigue a esta familia de matrices. Con el fin de preservar la simetr´ıa, cualquier intercambio de filas debe ser seguido por el intercambio de columnas correspondientes:     x 0 0 x x x x 0 0 x  0 x x 0 0   x x 0 0 0     3   0 x x 0 x  1↔  0 0 x x x  −→      x 0 0 x 0   0 0 x x 0  x 0 x 0 x x 0 x 0 x En los comandos

symrcm

symmmd

est´an implementados dos algoritmos de reordenaci´on muy populares: el algoritmo de Cuthill-McKee inverso y el algoritmo de m´ınimo grado. El primero reordena de forma que los t´erminos no nulos de la matriz tienden a estar concentrados cerca de la diagonal. El algoritmo de m´ınimo grado por su parte tiende a mover los elementos no nulos hacia el final de la matriz de forma que la estructura inicial de la matriz es esencialmente diagonal y el efecto relleno surge cuando el m´etodo de Gauss est´a ya muy avanzado. 2

Recuerda la colocaci´ on de los par´ antesis. O al menos matrices con estructura sim´etrica, esto es, a(i, j) 6= 0 ⇔ a(j, i) 6= 0. Todo lo que sigue es igualmente v´alido para este tipo de matrices. 3

72

´ II LECCION

Cap´ıtulo 5. Matrices sparse en Matematicas. Metodos iterativos

r do rra Bo Figura 5.1: Resultado de reordenar las filas y columnas con symrcm y symmmd.

Este tipo de t´ecnicas tuvieron su origen en la resoluci´on de ecuaciones en derivadas parciales mediante m´etodos num´ericos. Un buen ejemplo lo encontramos en la Figura 5.1 obtenido al aplicar estas dos reordenaciones a una matriz proveniente de la resoluci´on de la ecuaci´on de Laplace por elementos finitos. Observa como se reduce el n´ umero de entradas en las matrices L y U cuando se aplica alguno de los algoritmos anteriores (referido en la figura como nz). La descomposici´on LU debe calcularse sin pivotaje puesto que en otro caso el reordenamiento que introduce el m´etodo de Gauss con pivotaje arruina el orden introducido con los algoritmos de reordenamiento anteriores. Para ello se debe utilizar el comando >> [l,u]=lu(a,0);

El segundo argumento, que s´olo est´a disponible si la matriz a es sparse, fija un umbral para la realizaci´on del pivotaje parcial. El valor 1 es el de defecto. De esta forma, valores pr´oximos a cero obligan a que el pivotaje se produzca s´olo cuando el desequilibrio entre 73

´ II LECCION

5.1 M´etodo de Gauss para matrices sparse

el pivote y el resto de elementos de la columna sea muy acusado. Surge seguidamente la cuesti´on de estabilidad del m´etodo sin pivotaje. Afortunadamente para matrices definidas positivas o diagonal dominantes, el m´etodo de Gauss sin pivotaje es estable num´ericamente. La soluci´on del (o de los) sistemas se lleva a cabo con Soluci´ on con reordenamiento...

r do rra Bo 01 02 03 04

p=symmmd(a); [l,u]=lu(a(p,p)); x=l\b(p); x=u\x; x(p)=x;

% % % %

permutacion. vale tb p=symrcm(a); l y u son ahora "mas sparse" resolvemos los dos sistemas triangulares reordenamos las incognitas

En la l´ınea 01, el vector p recoge una permutaci´on de 1:n (n es el n´ umero de filas y columnas de a) que reduce el efecto relleno de L y U . La matriz a(p,p) es el resultado de reordenar ecuaciones e inc´ognitas. La l´ınea 04 reordena las inc´ognitas para recuperarlas en su orden original. Observa que la l´ınea 03 podr´ıa sustituirse simplemente por x=u\(l\b(p)); Nota. A partir de la versi´on 7.0, el comando symmmd que contiene el algoritmo de m´ınimo grado se ha declarado obsoleto y ser´a eliminado en futuras versiones. Se recomienda utilizar symamd.  Comentarios finales

Si la matriz es adem´as sim´etrica definida positiva podemos utilizar la descomposici´on de Cholesky, A = LL>

donde L es triangular inferior con elementos sobre la diagonal estrictamente positivos. El sistema se reduce ahora a dos sistemas triangulares L> x = y.

Ly = b,

La instrucci´on correspondiente en Matlab es chol, que devuelve R triangular superior de forma que A = R> R (es decir, en la notaci´on de estos apuntes, L = R> ). As´ı, el algoritmo anterior, con reordenaci´on adecuada, queda ahora Soluci´ on con reordenamiento... 01 02 03 04

p=symmmd(a); r=chol(a(p,p)); x=r’\b(p); x=r\x; x(p)=x;

% % % %

permutacion. vale tb p=symrcm(a); r es ahora "mas sparse" resolvemos los dos sist. triang. reordenamos las incognitas

74

´ II LECCION

Cap´ıtulo 5. Matrices sparse en Matematicas. Metodos iterativos

4

2 1

1

0 x x 0 0

x 0 0 x 0

0 x 0 0 x

5

3 x 0 0 0 0

1

x x x x x

0 x x 0 0

x x 0 x 0

0 x 0 0 x

x 0 0 0 0

x x 0 0 0

3 0 x x x x

x x x x x

5 0 x x x x

2

4

3 0 x x 0 0

5 0 x x x x

1

x 0 0 0 0

x x 0 0 0

3 0 x x 0 0

5 x x x x x

0 x x x x

x 0 0 0 0

x x 0 0 0

x x x x 0

r do rra Bo

x x x 0 x

4

2

4

2 1

5

3 x x 0 x 0

4

2

3

5

2

2

1

x 0 0 0 x

3

5

0 x x 0 x

0 x x 0 0

2

4

0 0 0 x x

x x 0 x x

1

x 0 0 0 0

3

5

0 x x 0 x

0 x x 0 0

2

4

0 0 0 x x

x x 0 x x

1

x 0 0 0 0

3

5

0 x 0 0 0

0 x x 0 x

x x x x x

1

x 0 0 0 0

3

1

4

2

4

0 0 0 x x

5

0 x 0 0 0

0 x x 0 0

4

0 0 0 x x

x x x x x

x 0 0 0 0

0 x 0 0 0

0 x x 0 0

0 0 0 x 0

Figura 5.2: Eliminaci´on gaussiana y su representaci´on como un grafo. Efecto del reordenamiento.

La orden x=a\b realiza todo el proceso anterior de forma autom´atica si a es sparse. Sin embargo en la forma que lo hemos expuesto podemos resolver reiteradamente sistemas de ecuaciones con la misma matriz de coeficientes al disponer de la descomposici´on LU ´o LL> .

Queda m´as all´a de los contenidos de este curso explicar c´omo funcionan los algoritmos implementados en symrcm y symmmd. Se puede se˜ nalar no obstante que ambos se basan en identificar la estructura de una matriz con la de un grafo no dirigido, donde dos nodos i y j est´an conectados si y s´olo si a(i,j)6=0. El proceso de eliminaci´on gaussiana se ve como la eliminaci´ on sistem´atica de nodos y la creaci´on de nuevos enlaces entre los nodos restantes. Concretamente, si hacemos un cero con la fila i en la fila j, aparecen nuevos enlaces entre los nodos que estaban unidos con el nodo i y los conectados con j. El problema se reescribe ahora en t´erminos de retirar los nodos en el orden adecuado de forma que se minimice el n´ umero de nuevos ejes creados (Figura 5.2).

Los gr´aficos de la Figura 5.1 han sido creados a trav´es del siguiente fichero script.

% Calculamos la matriz de elementos finitos para % un problema sobre un dominio en forma de L

[p,e,t]=initmesh(’lshapeg’,’Hmax’,0.2); % malla inicial 75

x x x x x

´ II LECCION

5.2 M´etodos iterativos para sistemas lineales

[p,e,t]=refinemesh(’lshapeg’,p,e,t); % refinamiento [a,b]=assempde(’lshapeb’,p,e,t,1,0,1); % a es la matriz (sparse) y b el termino independiente

r do rra Bo

% Primera fila de dibujos [l,u]=lu(a,0); % no pivotaje figure(1) subplot(331); spy(a); title(’matriz original’) subplot(332); spy(l); title(’matriz L’) subplot(333); spy(u); title(’matriz U’)

% Segunda fila de dibujos p=symrcm(a); % reordenamiento filas y columnas [l,u]=lu(a(p,p),0); figure(1) subplot(334); spy(a(p,p)); title(’matriz permutada con symrcm’) subplot(335); spy(l); title(’matriz L’) subplot(336); spy(u); title(’matriz U’) % Tercera fila de dibujos p=symmmd(a); % reordenamiento filas y columnas [l,u]=lu(a(p,p),0); figure(1) subplot(337); spy(a(p,p)); title(’matriz permutada con symmmd’) subplot(338); spy(l); title(’matriz L’) subplot(339); spy(u); title(’matriz U’)

5.2.

M´ etodos iterativos para sistemas lineales

Cuando un sistema de ecuaciones lineales es de tama˜ no moderado4 , casi nadie duda en utilizar el m´etodo de Gauss en alguna de sus m´ ultiples variantes (incluidas las descomposiciones matriciales). Sin embargo, la utilizaci´on de m´etodos iterativos se torna imprescindible en problemas con matrices grandes, especialmente si son sparse, donde el m´etodo de Gauss presenta las siguientes dificultades: Es caro: O(4n3 /3) operaciones

Es destructivo: retoca la matriz del sistema, y esto puede tener consecuencias muy poco deseables, como hemos visto con matrices sparse. Adem´as requieren en muchas ocasiones guardar una copia de la matriz.

4

Es dif´ıcil definir qu´e se entiende por tama˜ no moderado. Ciertamente, tama˜ nos enormes en la d´ecada de los a˜ nos 70 son ahora perfectamente manejables en un peque˜ no PC.

76

´ II LECCION

Cap´ıtulo 5. Matrices sparse en Matematicas. Metodos iterativos

Para obtener una soluci´on hace falta realizar todo el proceso: en pasos intermedios no se dispone de ninguna aproximaci´on de la soluci´on. Los m´etodos iterativos se introducen como un intento de salvar estas dificultades.

r do rra Bo 5.2.1.

Definici´ on

Esencialmente, un m´etodo iterativo toma un sistema lineal Ax = b

y construye una sucesi´on de vectores de forma que xm → x,

cuando m → ∞.

La forma de construir esta sucesi´on depende, obviamente de la matriz A, del t´ermino independiente y de c´omo se arranque el m´etodo num´erico (vector inicial). Existen multitud de esquemas diferentes pero la mayor´ıa comparten las siguientes desventajas: No siempre convergen en un n´ umero razonable de iteraciones, y en muchas ocasiones ni siquiera convergen.

Los resultados te´oricos sobre convergencia son a menudo pobres. Esto es, en general existe convergencia en situaciones mucho m´as generales de lo que la teor´ıa predice. Adem´as, chequear estas hip´otesis puede resultar tan costoso como resolver el mismo sistema.

El u ´ltimo punto merece cierto comentario. Los sistemas lineales provienen en general de problemas f´ısicos de los que se dispone de informaci´on a priori, entre las que se pueden encontrar las hip´otesis que aseguran la convergencia de un m´etodo iterativo. Por ejemplo, se puede saber que una matriz es definida positiva, y no hay necesidad por tanto de hacer esta comprobaci´on. Por contra, los m´etodos iterativos tienen las siguientes e importantes ventajas: Son m´etodos no destructivos. No modifican la matriz del sistema y, en general, precisan s´olo multiplicar por la matriz del sistema o por partes de ella. Suelen ser m´as estables frente a los errores de redondeo5 .

Se dispone en cada paso de una aproximaci´on de la soluci´on.

5

Carl Friedrich Gauss, que introdujo un m´etodo precursor del m´etodo conocido actualmente como m´etodo de Gauss–Seidel, comentaba en una carta a su colega Christian Ludwig que los c´alculos se pod´ıan realizar a´ un cuando “se estuviese medio dormido” o “pensando en cosas m´as importantes”. No hay que olvidar que en su ´epoca todos los c´alculos se hac´ıan a mano. En nuestros d´ıas, se plantea el mismo problema con los errores de redondeo.

77

´ II LECCION

5.2 M´etodos iterativos para sistemas lineales

5.2.2.

Detalles sobre la implementaci´ on

r do rra Bo

En un m´etodo iterativo no podemos esperar calcular la soluci´on exacta, sino hallar una aproximaci´on con una tolerancia prefijada. Por tanto debemos fijar un criterio de parada que d´e por terminado el m´etodo cuando la soluci´on se considere suficientemente buena. Esto no es grave. Los sistemas de ecuaciones lineales suelen provenir de m´etodos que calculan soluciones aproximadas de problemas f´ısicos e ingenieriles. No tiene pues sentido obcecarse en calcular la soluci´on exacta de un problema aproximado. As´ı hemos de elegir un criterio de parada que termine la ejecuci´on cuando la soluci´on es suficientemente buena. Una posibilidad es medir la diferencia entre dos iteraciones consecutivas kxm+1 − xm k

en alguna norma que queda a elecci´on del programador o del usuario. Si la diferencia es peque˜ na, se considera que estamos cerca de la soluci´on y se finaliza el m´etodo. De nuevo nos encontramos con el problema de definir peque˜ no. Por ejemplo, una diferencia de 1.4 entre dos iteraciones puede ser grande si la soluci´on tiene un tama˜ no na si kxk ≈ 1010 . kxk ≈ 10−1 o peque˜ Por ello se puede hacer un promedio entre el error absoluto y el relativo. Concretamente, si x e y son dos iteraciones consecutivas, se puede fijar el criterio 01 02 03 04 05

aux=norm(x-y); % norma 2 entre x e y if (aux A)

r do rra Bo

donde ρ(B), denominado radio espectral, denota el mayor de los valores absolutos de los valores propios de B (ver Lecci´on IV). Si A es sim´etrica, se tiene simplemente que kAk2 = ρ(A). En cualquier caso, el comando norm de Matlab aplicado a matrices devuelve las correspondientes normas matriciales: >> norm(a,1) >> norm(a,inf) >> norm(a,2)

% norma 1 % norma infinito % norma 2. Vale tambien norm(a)

Una norma vectorial y su norma matricial inducida se relacionan mediante kAxk | {z }

norma vectorial



kAk |{z}

norma matricial

kxk |{z}

.

norma vectorial

Es decir, kAk mide el m´aximo alargamiento que multiplicar por A puede producir en un vector medido en la norma k · k. Definici´ on y condiciones de convergencia

Los m´etodos iterativos lineales (o basados en iteraciones afines) comienzan considerando una partici´on de A tal que A=M −N

con M invertible. As´ı, si x es soluci´on de Ax = b,

M x = N x + b.

El m´etodo iterativo consiste en

Tomar x0 una aproximaci´on de la soluci´on. Si no se conoce se puede tomar por ejemplo el vector nulo. Resolver en cada paso m

M xm+1 = N xm + b.

(5.1)

Es f´acil ver que si la sucesi´on construida en (5.1) converge a alg´ un x, entonces el vector es la soluci´on del sistema. A´ un es m´as, se comprueba f´acilmente que xm+k+1 − x = (M −1 N )(xm+k − x) = . . . = (M −1 N )k (xm+1 − x).

Denotando por B = M −1 N se tiene el siguiente resultado

Teorema 5.1 El m´etodo iterativo converge si y s´olo si existe k tal que kB k k < 1. 80

´ II LECCION

Cap´ıtulo 5. Matrices sparse en Matematicas. Metodos iterativos

r do rra Bo

Observa que en el resultado anterior no se especifica la norma utilizada. Otro detalle al que a veces se presta poca atenci´on es que la convergencia del m´etodo ocurre sea cu´al sea x0 , es decir, independientemente de c´omo se arranque el m´etodo y de cu´al sea el t´ermino independiente. Claramente si se tiene una estimaci´on buena de la soluci´on el m´etodo converger´a en menos iteraciones, pero no es una condici´on imprescindible para asegurar la convergencia7 . No es dif´ıcil ver que ρ(B) ≤ kBk

para cualquier norma inducida, y por tanto8

ρ(B) = (ρ(B k ))1/k ≤ (kB k k)1/k

∀k ∈ N.

Es m´as, se puede probar que, de nuevo para toda norma inducida, l´ım kB k k1/k = ρ(B)

k→∞

Por tanto se concluye que una condici´ on equivalente de convergencia es que todos los valores propios de B = M −1 N tengan valor absoluto menor estrictamente que 1.

Teorema 5.2 El m´etodo iterativo converge si y s´olo si ρ(B) < 1. Los resultados anteriores pueden utilizarse para probar que kxm+1 − xk ≤ C(m)ρ(B)m kx1 − x0 k

para todo m ≥ m0 y donde C(m) ≥ 1, con C(m) → 1 cuando m → ∞. La cantidad ρ(B) recibe en ocasiones el nombre de velocidad asint´ otica de convergencia. La estimaci´on anterior justifica esta denominaci´on dado que mide la reducci´on media del error esperada en cada iteraci´on.

Nota. Si M = A entonces N = 0, por tanto B = 0 y trivialmente ρ(B) = 0.

Es decir, hay convergencia en una u ´nica iteraci´on. Esta iteraci´on consiste en resolver directamente el sistema de ecuaciones. En general, uno asegura la convergencia cuando M recoge la informaci´on m´as importante de A, de forma que N = M − A tenga un tama˜ no peque˜ no comparado con M . Por otro lado, se debe tener en cuenta la definici´on del m´etodo (5.1) y que por tanto en cada iteraci´on hay que resolver un sistema de ecuaciones. As´ı, interesa que M sea sencilla desde el punto de vista de la resoluci´on del sistema lineal (por ejemplo, diagonal, triangular,...) y que simult´aneamente recoja la mayor informaci´on posible de A.  7

Esta propiedad se pierde cuando se resuelven ecuaciones y sistemas no lineales. En este caso, los m´etodos num´ericos convergen s´ olo si se arranca suficientemente cerca de la soluci´on. 8 Si λ es valor propio de B, λ2 lo es de A2 .

81

´ II LECCION

5.2 M´etodos iterativos para sistemas lineales M´ etodos de Jacobi, de Gauss–Seidel y de relajaci´ on de Young Sea el sistema Ax = b donde 

 . . . a1n . . . a2n   ..  .. . .  . . . ann

r do rra Bo

  A= 

a11 a12 a21 a22 .. .. . . an1 an2

La familia de m´etodos que vamos a exponer se basa en considerar la siguiente descomposici´on de A A=D−L−U

donde 



a11

  D = 

a22

..



    , L =   

.

ann

0 −a21 .. .

0 0 .. .

··· ··· .. .



0 0 .. .



    , U =   

−an1 −an2 · · · 0

0 −a12 0 0 .. .. . . 0 0

· · · −a1n · · · −a2n .. .. . . ··· 0



  . 

El m´ etodo de Jacobi consiste en tomar en la definici´on del m´etodo iterativo M = D y N = L + U , es decir, Dxm+1 = (L + U )xm + b.

Para calcular xm+1 hay que resolver por tanto un sistema diagonal cuyo coste es despreciable. Visto componente a componente, tenemos que si h i> (m) (m) xm = x1 , x2 , . . . , x(m) ∈ Rn n entonces

(m+1)

xi

=

i X 1h (m) aij xj , bi − aii j6=i

i = 1, . . . , n.

Para algunos tipos especiales de matrices se sabe que el m´etodo converge e incluso se dispone de informaci´on sobre la velocidad de convergencia. Una matriz es estrictamente diagonal dominante por filas si X |aii | > |aij |, ∀i j6=i

y por columnas si

|ajj | >

X

|aij |,

∀j.

i6=j

Teorema 5.3 Si la matriz es estrictamente diagonal dominante por filas o columnas el m´etodo de Jacobi converge.

Ejercicio 5.1 (matem´ atico) Probar el teorema anterior. ¿Cu´ando converger´a m´as r´apido? (Ayuda. Construir la matriz B = D−1 (L + U ). Probar que kBk∞ < 1 si es dominante por filas ´o kBk1 < 1 si es dominante por columnas. Aplicando el Teorema 5.2, se deduce el resultado.)

82

´ II LECCION

Cap´ıtulo 5. Matrices sparse en Matematicas. Metodos iterativos

Para dar una descripci´on del m´etodo de Jacobi en pseudoc´odigo fijamos x = aproximaci´on inicial, eps1 = tolerancia absoluta,

mmax = eps2 =

n´ umero m´aximo de iteraciones, tolerancia relativa,

r do rra Bo

y tomamos como criterio de parada la norma eucl´ıdea de la diferencia entre dos iteraciones sucesivas del m´etodo. La elecci´on de la norma es libre, queda a elecci´on del programador (pod´ıamos tomar por ejemplo la norma 2 o la norma infinito). Una primera versi´on de nuestro algoritmo es la siguiente Jacobi 01 02 03 04

for m=1:mmax error=0; y=x for i=1:n n   X x i = bi − aij yj /aii j=1 j6=i

05 06 07 08 09 10 11

end if kx − yk2 2 mmax=varargin{1}; end if nargin>3 eps1=varargin{2}; end if nargin>4 eps2=varargin{3}; end if nargin>5 x(:)=varargin{4}; %x es un vector columna end % Metodo de Jacobi

for m=1:mmax error=0; y=x; for i=1:n v=[1:i-1 i+1:n]; x(i)=(b(i)-a(i,v)*y(v))/a(i,i); end error=norm(x-y); % otras normas con norm(x-y,1),norm(x-y,inf) if (error1) varargout{1}=m; 84

´ II LECCION 59 60

Cap´ıtulo 5. Matrices sparse en Matematicas. Metodos iterativos

end return

r do rra Bo

Recuerda que el comando break, utilizado en la l´ınea 48 provoca la salida autom´atica del bucle, dando por finalizado la ejecuci´on del m´etodo y pasando a la parte del c´odigo encargada de devolver los resultados obtenidos.  Ejercicio 5.3 Programa una nueva opci´on de salida que devuelva un vector error de longitud m − 1 de forma que error(m) sea la diferencia entre xm y xm+1 .

Observa que el c´odigo realmente dedicado al m´etodo de Jacobi se reduce a apenas diez l´ıneas (39-50) con el resto de la subrutina dedicada al control del algoritmo y a la salida y entrada de datos. Se observa adem´as que la l´ınea 43 permite implementar en una u ´nica l´ınea (44) el producto de la l´ınea 04 del pseudoc´odigo. El c´odigo anterior, sin embargo, es optimizable. El ejercicio siguiente ahonda en un aspecto en particular

Ejercicio 5.4 Otra forma alternativa de implementar el m´etodo es reemplazar las l´ıneas 42-45 por el producto x=(b-a*y+d.*y)./d

o bien

x=y+(b-a*y)./d

donde d es un vector columna que contiene la diagonal de la matriz. Observa que realizamos operaciones de m´as (multiplicamos por la diagonal para luego restar su contribuci´on), pero el costo es despreciable y la operaci´on es ahora puramente matricial. Implementa esta nueva forma y comprueba el resultado. ¿Obtienes mejoras en el redimiento del m´etodo9 ? El m´ etodo de Gauss–Seidel10 consiste en tomar M = D − L y N = U , es decir (D − L)xm+1 = U xm + b.

(5.2)

Para calcular xm+1 hay que resolver un sistema, en este caso triangular. Repasando con cuidado las operaciones, observamos que (m+1) xi

i−1 n i X X 1h (m+1) (m) = bi − aij xj − aij xj , aii j=1 j=i+1

9

i = 1, . . . , n.

Deber´as probar con matrices grandes. La orden rand te puede servir para ese fin. Una forma de asegurar la convergencia es generar matrices estrictamente diagonal dominantes. ¿C´omo se puede hacer esto?. 10 El nombre de este algorimo es muy curioso. Seg´ un diversos autores (ej. George E. Forsythe ´o Gerard Meurant), Carl Friedrich Gauss no dise˜ n´ o exactamente este m´etodo y Philipp Ludwig von Seidel, que lo estudi´o a finales del siglo XIX, desaconsejaba su uso. Gauss desarroll´o un m´etodo muy similar cuando trataba de resolver un problema de geodesia que llevaba a un sistema lineal que no era compatible determinado.

85

´ II LECCION

5.2 M´etodos iterativos para sistemas lineales Escrito en forma algor´ıtmica, Gauss–Seidel for m=1:mmax error=0; y=x for i=1:n i−1 n   X X x i = bi − aij xj − aij yj /aii

r do rra Bo

01 02 03 04

j=1

05 06 07 08 09 10 11

j=i+1

end if kx − yk 1. De ah´ı el nombre que se le da a veces de Sobrerrelajaci´on (overrelaxed). 87

´ II LECCION

5.2 M´etodos iterativos para sistemas lineales

Por u ´ltimo, aunque no sea inmediato, se puede comprobar que este m´etodo encaja en el marco anterior, sin m´as que tomar M=

1 D − L, ω

N=

1−ω D+U ω

r do rra Bo

Ejercicio 5.9 Implementa el m´etodo de relajaci´on de Young a partir del m´etodo de Gauss– Seidel. Incluye como nuevo argumento de entrada el par´ametro ω. Un posible valor por defecto podr´ıa ser ω = 1 con lo que tendr´ıamos el m´etodo de Gauss–Seidel.

Ejercicio 5.10 De nuevo, la parte central del m´etodo de relajaci´on se puede implementar en la forma x=y+m\(b-a*y)

donde m es una matriz adecuada. ¿Cu´al es esa matriz?.

5.2.4.

M´ etodos de tipo gradiente

Comenzaremos recordando algunos conceptos e introduciendo algunas notaciones que facilitar´an la exposici´on de los m´etodos de tipo gradiente. Recordemos que todos los vectores se consideran como vectores columna. Dada A una matriz sim´ etrica definida positiva, la operaci´on que a cada par de vectores x, y le asigna el n´ umero real x> Ay es un producto escalar, esto es, cumple las propiedades que definen un producto escalar11 : 1. (αx + βy)> Az = αx> Az + βy> Az,

∀α, β ∈ R, ∀x, y, z ∈ Rn ;

2. x> Ay = y> Ax, ∀x, y ∈ Rn (por ser A sim´etrica); 3. x> Ax > 0,

si x 6= 0 (por ser A definida positiva).

En particular, si In es la identidad n × n,

x> In y = x> y

es simplemente el producto escalar habitual en Rn de x e y. Denotaremos x⊥y

⇐⇒

x> y = 0

y diremos en este caso que x e y son ortogonales. La misma notaci´on se puede extender al producto definido por A, de forma que x ⊥A y

⇐⇒

x> Ay = 0

y en este caso x e y se dicen A−ortogonales. 11

Es interesante observar cu´ antas propiedades del producto escalar eucl´ıdeo (el habitual en Rn ) dependen u ´nicamente de que se cumplan estas tres propiedades y por tanto son extensibles a estos casos m´as generales.

88

´ II LECCION

Cap´ıtulo 5. Matrices sparse en Matematicas. Metodos iterativos

La norma asociada al producto escalar anterior se conoce como norma de energ´ıa y su expresi´on viene dada, obviamente, por √ kxkA := x> Ax.

r do rra Bo

Todas las normas son equivalentes en Rn , pero para esta norma se tiene adem´as la estimaci´on λn kxk2 ≤ kxkA ≤ λ1 kxk2

donde λ1 ≥ λ2 ≥ .... ≥ λn > 0 son los valores propios, todos reales por ser A sim´etrica y positivos por ser definida positiva. La cantidad κ(A) =

λ1 , λn

que ser´a relevante en lo que sigue, es el condicionamiento de la matriz12 . Obviamente, κ(A) ≥ 1. Construimos la funci´on F (x) = 12 x> Ax − x> b conocida como funcional de energ´ıa. Tras unos simples c´alculos, se comprueba que ∇F = Ax − b.

Por tanto, el u ´nico posible extremo de F es la soluci´on de Ax − b = 0. Adem´as, como la matriz hessiana de F es la propia matriz A, que es definida positiva, este extremo ser´a un m´ınimo. Hemos llegado por tanto a la siguiente conclusi´on: resolver Ax = b es equivalente a encontrar el m´ınimo de F

En esta observaci´on se basan los m´etodos de descenso: en lugar de resolver el sistema de ecuaciones Ax = b, nos preocupamos en buscar el m´ınimo de F . Es esencial que A sea definida positiva para que estos argumentos sean v´alidos. M´ etodos de descenso. Aspectos generales

La idea de estos m´etodos es sencilla. Dado un valor inicial consiste en ir movi´endose en trayectorias zigzagueantes hasta alcanzar el m´ınimo. Concretamente, dada una aproximaci´on, fijamos una direcci´on de desplazamiento, calculamos cuanto nos movemos, descender en el lenguaje habitual, y nos desplazamos a un nuevo punto. De esta forma construimos una sucesi´on xm que deber´ıa converger a x, siguiendo estos pasos. Calcular una direcci´on de descenso dm .

Descender una cantidad ξm , tomando como nueva aproximaci´on xm+1 = xm + ξm dm .

12

El condicionamiento se define tambi´en para matrices arbitrarias reemplazando los valores propios por los denominados valores singulares, o m´ as en general, defini´endolo como el producto de la norma de A por la norma de su inversa. En general el condicionamiento de la matriz mide la sensibilidad del sistema de ecuaciones lineales asociado a variaciones del t´ermino independiente.

89

´ II LECCION

5.2 M´etodos iterativos para sistemas lineales

Se procede as´ı hasta que hay convergencia. Dos aspectos determinan el m´etodo: qu´e direcci´on se toma y cu´anto se desciende. Tanto en el m´etodo del Gradiente como en el m´etodo del Gradiente Conjugado, que veremos a continuaci´on, se toma ξm de forma que

r do rra Bo

F (xm+1 ) = m´ın F (xm + α dm ) α∈R

es decir, se trata de minimizar, una vez escogida la direcci´on de descenso dm , el funcional de energ´ıa. Definiendo g(α) = F (xm + α dm ) podemos comprobar que

> g 0 (α) = α d> m Adm − dm (b − Axm ) | {z }

rm

y por tanto la cantidad de descenso viene dada por ξm :=

r> m dm , > dm Adm

(5.3)

(obtenido al imponer g 0 (α) = 0). El vector rm = b − Axm es el residuo de xm , que ya ha surgido en estas notas. Se puede probar f´acilmente que rm+1 = b − Axm+1 = b − Axm − ξm Adm = rm − ξm Adm .

En consecuencia, el residuo en pasos sucesivos satisface una relaci´on similar a la que cumple xm . Sin embargo, este tipo de recurrencia puede verse afectada por errores de redondeo, por lo que en ocasiones el residuo se recalcula cada cierto n´ umero de iteraciones de acuerdo a su definici´on para cancelar cualquier error de redondeo. El algoritmo resultante es el siguiente: M´ etodo de descenso 01 02 03 04

05 06 07

x0 inicial, r0 = b0 − Ax0 for m=0:mmax Escoger dm r > dm ξm := >m dm Adm xm+1 = xm + ξm dm rm+1 = rm − ξm Adm end

Claramente, la l´ınea 03 queda pendiente y en u ´ltima medida define el m´etodo. 90

´ II LECCION

Cap´ıtulo 5. Matrices sparse en Matematicas. Metodos iterativos

M´ etodo del Gradiente Dado que −∇F (xm ) = b − Axm = rm , la direcci´on de m´aximo descenso es la del residuo. Por tanto, ´esta parece una buena elecci´on para dm . El m´etodo as´ı definido es el m´etodo del gradiente.

r do rra Bo M´ etodo del Gradiente 01 02 03

x0 inicial; r0 = b − Ax0 ; for m=0:mmax pm = Arm r> m rm > r m pm xm+1 = xm + ξm rm rm+1 = rm − ξm pm if krm+1 k ≤ epskbk break end ξm =

04

05 06 07 08 09 10

end

En el paso 06 estamos calculando el residuo de la soluci´on. El criterio de parada se toma ahora a partir del residuo. En concreto hemos escogido el basado en el tama˜ no relativo del residuo (epskbk). La norma que utilizamos es la eucl´ıdea, que es connatural al m´etodo. Ejercicio 5.11 Programa el M´etodo del Gradiente.

Soluci´ on. Una posible implementaci´on del m´etodo es la que sigue 01 02 03 04 05 06 07 08 09 10 11 12 13 14 15

% GRADIENTE % % X = GRADIENTE(A,B) % % % X = GRADIENTE(A,B,ITMAX) % % X = GRADIENTE(A,B,ITMAX... % EPS) % % X = GRADIENTE(A,B,ITMAX... % EPS, X0) % %[X,IT] = GRADIENTE(A,B,ITMAX... % EPS,XO) 91

Aplica el met. del gradiente para la resolucion del sistema AX=B

ITMAX: numero max. de iteraciones EPS tolerancia relativa

X0 es el valor inicial

Devuelve en IT el numero de iteraciones calculadas

´ II LECCION

5.2 M´etodos iterativos para sistemas lineales

%[X,IT,R]= GRADIENTE(A,B,ITMAX) % EPS,XO)

R es un historial del metodo: R(i) es el residuo en el paso i

function [x,varargout]= gradiente(a,b,varargin);

r do rra Bo

16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56

n=length(a); x=zeros(n,1); mmax=40; tol=1e-6; if nargin>2 mmax=varargin{1}; end if nargin>3 tol=varargin{2}; end if (nargin>4) x=varargin{4}; end

r=b-a*x; res(1)=dot(r,r); aux=norm(b); for m=1:mmax p=a*r; xi=res(m)/dot(r,p); x=x+xi*r; r=r-xi*p; res(m+1)=dot(r,r); % guardamos los residuos if (sqrt(res(m+1))1 varargout{1}=m; end if nargout>2 varargout{2}=sqrt(res(:)); end return

El vector res guarda el residuo en cada iteraci´on para as´ı tener un historial de como ha ido la convergencia. Prueba el m´etodo con un sistema donde la matriz sea sim´etrica definida positiva (nota: para toda matriz B, B > B es sim´etrica (semi) definida positiva.) 92

´ II LECCION

Cap´ıtulo 5. Matrices sparse en Matematicas. Metodos iterativos 

La gr´afica mostrada en la Figura 5.3 se ha construido utilizando las instrucciones n=40;a=rand(n,n); a=a*a’; %% a es sim\’{e}trica definida positiva x=ones(n,1); b=a*x; [x,it,r]=gradiente(a,b,100,1e-5); semilogy(r)

r do rra Bo

>> >> >> >>

Hemos utilizado una escala logar´ıtmica para medir la norma del residuo. Observa su fuerte comportamiento oscilatorio.

10

10

10

10

10

10

10

Residuo

4

3

2

1

0

−1

−2

0

10

20

30

40

50

60

70

Iteraciones

Figura 5.3: Historial del residuo para el m´etodo del Gradiente.

Ejercicio 5.12 En este ejercicio tratamos de nuevo aspectos de la implementaci´on en Matlab. Concretamente, ¿qu´e pasa si el usuario desea especificar el vector de arranque (x0 en la notaci´on del m´etodo) pero desea dejar el n´umero m´aximo de iteraciones y la tolerancia por defecto?. Como est´andar en Matlab, se env´ıa vac´ıo ([ ]), de forma que los argumentos intermedios se ignoran. Por ejemplo, >> x=gradiente(a,b,[],1e-5)

especificar´ıa la tolerancia pero no el n´umero m´aximo de iteraciones. Implementa las modificaciones necesarias en el programa anterior para que la funci´on soporte este est´andar. (Ayuda: La funci´on isempty puede resultarte u ´til.)

Breves notas sobre el estudio del M´ etodo del Gradiente La clave del an´alisis es la relaci´on

F (xm+1 ) − F (x) = 21 (xm+1 − x)> A(xm+1 − x) = 12 k xm+1 − x k2A | {z } em+1 93

´ II LECCION

5.2 M´etodos iterativos para sistemas lineales

donde claramente em+1 es el error entre la soluci´on exacta y la num´erica medido en la norma de energ´ıa de A. Por tanto, como F (xm+1 ) ≤ F (xm ), kem+1 kA ≤ kem kA

r do rra Bo

luego en cada iteraci´on hay una reducci´on del error en la norma de energ´ıa. Sin embargo, en ning´ un caso implica que el residuo se reduzca en cada iteraci´on, como bien podemos un es m´as, de la elecci´on hecha de ξm se sigue que comprobar en la Figura 5.3. A´ F (xm+1 ) := m´ın F (xm + α rm ) α∈R

y por tanto

h

i

kem+1 kA ≤ m´ın kx − xm − α rm kA = m´ın kem − αAem kA ≤ m´ın kI − αAkA kem kA . α∈R

α∈R

α∈R

Observa que hemos utilizado la cota kM xkA ≤ kM kA kxkA , caracter´ıstica de toda norma vectorial y su norma matricial inducida.

Proposici´ on 5.5 Sean λ1 y λn el mayor y menor valor propio de A. Entonces m´ın kI − αAkA = m´ın kI − αAk2 = α∈R

α∈R

λ1 − λ n < 1. λ1 + λ n

La convergencia se escribe de forma muy c´omoda en t´erminos del condicionamiento de la matriz κ(A) = λλn1 , deduciendo la expresi´on kem+1 kA ≤

κ(A) − 1 kem kA . κ(A) + 1

Es inmediato observar que

El factor de reducci´on del error es siempre menor que uno, luego hay convergencia para toda A sim´etrica definida positiva. Si κ(A) >> 1, la convergencia puede ser muy lenta.

Ejercicio 5.13 (puramente matem´ atico) Se puede probar que dada A sim´etrica definida positiva existe B sim´etrica definida positiva tal que BB > = B 2 = A, conocida como ra´ız cuadrada de A. Utilizando este resultado prueba la identidad kI − αAkA = kI − αAk2

utilizada en la Proposici´on 5.5.

(Ayuda: Observa que kxkA = kBxk2 . Utiliza ahora que

kI − αAkA = sup k(I − αA)xkA = sup kB(I − αA)B −1 (Bx)k2 kxkA =1

kBxk=1

y completa la demostraci´on).

94

´ II LECCION

Cap´ıtulo 5. Matrices sparse en Matematicas. Metodos iterativos

Ejercicio 5.14 (demostraci´ on de la Proposici´ on 5.5) Para toda matriz sim´etrica C se cumple que kCk2 = m´ax |λj | j

con λj el valor propio j−´esimo. Por tanto

r do rra Bo kI − αAkA = kI − αAk2 = m´ax |1 − αλj |. j

Define gc (α) = |1 − c α| y traza la gr´afica de estas funciones para varios valores de c. Deduce que α = 2/(λ1 + λn ) es el valor que hace m´ınimo kI − αAk2 y que para este valor, kI − αAk2 =

λ1 − λ n . λ1 + λn

(Ayuda: al dibujar gc (α) para diferentes valores de c obtendr´as obtendr´as algo similar a esto

1

0.5

0 0

1

2

α

3

4

5

¿Cu´ales son las gr´aficas de los valores extremos?)

El Gradiente Conjugado

El m´etodo del Gradiente Conjugado trata de resolver alguna de las dificultades observadas con el m´etodo del Gradiente, como por ejemplo el comportamiento oscilatorio del residuo. Observemos que en un m´etodo de descenso, y por la elecci´on de ξm hecha en (5.3), > > r> m+1 dm = rm dm − ξm dm Adm = 0,

por lo que rm+1 ⊥ dm . Esto es, en un m´etodo de descenso el residuo del paso m + 1 es ortogonal a la direcci´ on de descenso anterior. Sin embargo, en general ya no es cierto que rm+1 ⊥ dm−1 y por tanto se pierde esta propiedad de ortogonalidad. 95

(5.4)

´ II LECCION

5.2 M´etodos iterativos para sistemas lineales

Una forma de evitar, o de mitigar, el aspecto oscilante del m´etodo del Gradiente, es exigir que la direcci´on de descenso dm satisfaga (5.4). Es decir, tomamos rm+1 = rm − ξm Adm ,

r do rra Bo

y concluimos que

d> m−1 rm+1 = 0

⇐⇒

dm−1 ⊥ Adm

⇐⇒

dm−1 ⊥A dm .

En vista de lo anterior optamos por tomar como direcci´on de descenso una perturbaci´on de la direcci´on natural rm (el residuo) en la direcci´on del descenso anterior (dm−1 ) que satisfaga la propiedad de ortogonalidad anterior. Es decir, tomamos dm = rm + τm dm−1

con τm adecuado. Exigiendo que se satisfaga (5.4) deducimos que dm ⊥A dm−1

⇐⇒

> r> m Adm−1 + τm dm−1 Adm−1 = 0

⇐⇒

τm = −

r> m Adm−1 . > dm−1 Adm−1

Como elecci´on inicial de la direcci´on de descenso tomamos simplemente r0 , el residuo de la aproximaci´on inicial. Con todo esto, la primera versi´on del m´etodo del Gradiente Conjugado es la que sigue Gradiente Conjugado - Primera versi´on 01 02 03

x0 inicial; r0 = b − Ax0 ; d0 = r0 ; for m=0:mmax pm = Adm r> m dm d> m pm

04

ξm =

05 06 07 08 09

xm+1 = xm + ξm dm rm+1 = rm − ξm pm if krm+1 k ≤ epskbk break end r > pm τm+1 = − m+1 d> m pm dm+1 = rm+1 + τm+1 dm

10

11 12 13

end disp(’Numero maximo de iteraciones alcanzado’)

Como puede verse, las modificaciones sobre el m´etodo del Gradiente son m´ınimas y est´an concentradas en las l´ıneas 04, 10 y 11. En cuanto al n´ umero de operaciones, 96

´ II LECCION

Cap´ıtulo 5. Matrices sparse en Matematicas. Metodos iterativos

coincide con las del m´etodo del Gradiente: en cada paso es necesario calcular un producto matriz–vector (l´ınea 03) y tres productos escalares (04 y 10). Listaremos a continuaci´on algunas propiedades entre los residuos y las direcciones de descenso que permiten dar una expresi´on distinta del m´etodo, y deducir alguna de las propiedades de convergencia.

r do rra Bo Lema 5.6 Para todo m ≥ 0

> r> m dm = r m r m .

Por tanto

ξm =

r> m rm . d> m Adm

Demostraci´on. Como rm ⊥ dm−1 ,

> > r> m dm = rm rm + τm rm dm−1 . | {z }

(5.5)

=0

El segundo resultado es inmediato de la definici´on de ξm .



Lema 5.7 Para todo m ≥ 0 se satisfacen las siguientes relaciones i) dm+1 ⊥A dm .

ii) rm+1 ⊥ dm ,

rm+1 ⊥ dm−1 .

iii) rm+1 ⊥ rm .

Demostraci´on. Los puntos i) y ii) ya se han probado. Para probar iii) basta comprobar que > > > > > r> m+1 rm = rm rm − ξm dm Arm = rm rm − ξm dm Adm + ξm τm dm Adm−1 | {z } =0

=

r> m rm



ξm d> m Adm .

El resultado es ahora una consecuencia del Lema 5.6. Lema 5.8 Para todo m ≥ 0

τm+1



rm+1 r> := m+1 . > rm rm

Demostraci´on. Como

−Adm =

1 (rm+1 − rm ), ξm

se tiene

τm+1 = −

r> r> 1 r> 1 r> m+1 Adm m+1 (rm+1 − rm ) m+1 rm+1 m+1 rm+1 = = = > > > dm Adm ξm dm Adm ξm dm Adm r> m rm

donde hemos utilizado que rm+1 ⊥ rm , y en el u ´ltimo paso, la expresi´on alternativa de ξm .  Los Lemas 5.6 y 5.8 dan expresiones m´as simples de los par´ametros ξm y τm . De hecho m´as econ´omicas, dado que r> m rm es conocido del paso anterior y por tanto no es preciso calcularlo de nuevo. En total dos productos escalares por iteraci´on. 97

´ II LECCION

5.2 M´etodos iterativos para sistemas lineales

Ejercicio 5.15 Modifica el algoritmo del Gradiente Conjugado con las nuevas expresiones de ξm y τm . Observa que podemos evitar en esta versi´on un producto escalar por iteraci´on. El resultado sorprendente, y que descubre parte de las buenas propiedades del Gradiente Conjugado, es que estas propiedades de ortogonalidad se extienden a todo el conjunto de residuos y direcciones generados en los pasos anteriores.

r do rra Bo Lema 5.9 Para todo m ≤ n i) dm ⊥A d` ,

∀` ≤ m − 1;

ii) rm+1 ⊥ d` ,

∀` ≤ m;

iii) rm+1 ⊥ r` ,

` ≤ m.

La tercera propiedad implica en particular la convergencia del Gradiente Conjugado en aritm´etica exacta en a lo sumo n pasos dado que no puede haber n+1 vectores ortogonales en Rn y por tanto rn+1 = 0. Sin embargo, en aplicaciones pr´acticas puede requerir m´as de n iteraciones por los errores introducidos por la precisi´on de la m´aquina. Ejercicio 5.16 Modifica el programa gradiente para implementar en una funci´on de nombre gradconjugado el m´etodo del Gradiente Conjugado. Hemos ejecutado como antes

>> n=40;a=rand(n,n); a=a*a’; x=ones(n,1); b=a*x; >> [x,it,r]=gradconjugado(a,b,100,1e-5); >> semilogy(r)

y hemos desplegado en la Figura 5.4 las normas de los residuos en cada paso. Como se

10

10

10

10

10

10

10

Residuo

4

3

2

1

0

−1

−2

0

2

4

6

8

Iteraciones

10

12

14

Figura 5.4: Historial del residuo para el m´etodo del Gradiente Conjugado

puede comprobar la convergencia es m´as r´apida y hemos reducido notablemente el molesto comportamiento oscilatorio del residuo. 98

´ II LECCION

Cap´ıtulo 5. Matrices sparse en Matematicas. Metodos iterativos

An´ alisis del m´ etodo

r do rra Bo

En esta secci´on probaremos el Lema 5.9. El lector m´as interesado en la implementaci´on del m´etodo puede saltar esta secci´on sin mayor problema. Animamos, no obstante, a su lectura pues ilustra un conjunto de t´ecnicas habituales en otras familias de m´etodos iterativos. Adem´as sirve de ejemplo que demostrar el buen funcionamiento de un esquema num´erico m´as elaborado, generalmente obtenido mediante modificaciones intuitivas de algoritmos m´as simples, puede requerir un an´alisis nada trivial. Tampoco es extra˜ na la situaci´on contraria: un m´etodo puede fallar por razones no inmediatamente comprensibles. En la demostraci´on juega un papel muy importante el subespacio Km (A, r0 ) := Rhr0 , Ar0 , . . . , Am r0 i

esto es, el subespacio formado por todas las combinaciones lineales α0 r0 + α1 Ar1 + . . . + αm Am r0 ,

αi ∈ R.

Estos subespacios reciben el nombre de subespacios de Krylov y son clave en multitud de m´etodos num´ericos para la resoluci´on de sistemas lineales. Antes de proseguir haremos unos simples comentarios: 1. El subespacio tiene a lo sumo dimensi´on m + 1.

2. Si q ∈ Km (A, r0 ), entonces Aq ∈ Km+1 (A, r0 ). Es decir, AKm (A, r0 ) ⊂ Km+1 (A, r0 ). 3. Si Km (A, r0 ) = Km+1 (A, r0 ), entonces Km (A, r0 ) = Km+1 (A, r0 ) = Km+2 (A, r0 ) = ... 4. Es f´acil comprobar que rm , dm ∈ Km (A, r0 ).

La demostraci´on del Lema 5.9 se llevar´a a cabo por inducci´on sobre m. Para m = 0 es un simple ejercicio de comprobaci´on (en este caso r0 = d0 y por tanto ii) y iii) coinciden). Supongamos pues que el resultado est´a probado para m. Concretamente, supongamos que para m i) dm ⊥A d` ,

∀` ≤ m − 1 y {d0 , d1 , . . . , dm } es una base de Km (A, r0 ).

ii) rm+1 ⊥ d` ,

∀` ≤ m.

iii) rm+1 ⊥ r` ,

` ≤ m y {r0 , r1 , . . . , rm+1 } es una base ortogonal de Km+1 (A, r0 ).

Veamos que los puntos i)–iii) se satisfacen entonces para m + 1.

i) dm+1 ⊥A d` ,

∀` ≤ m:

99

´ II LECCION

5.2 M´etodos iterativos para sistemas lineales

Este resultado est´a probado ya para ` = m. Para ` ≤ m − 1, utilizamos que dm+1 = rm+1 + τm+1 dm . Por tanto, basta probar que dm ⊥A d` .

r do rra Bo

rm+1 ⊥A r` ,

El segundo es ya conocido (hip´otesis de inducci´on). Por otro lado rm+1 ⊥A r`

⇐⇒

rm+1 ⊥ Ar` .

Como Ar` ∈ K`+1 (A, r0 ) y una base de este subespacio es {r0 , r1 , . . . , r`+1 } ⊂, concluimos que Ar` = α0 r0 + α1 r1 + . . . + α`+1 r`+1

con αj ∈ R adecuados. El resultado se sigue ahora de iii) puesto que rm+1 ⊥ rk , para todo k ≤ m. Por u ´ltimo si dm+1 6= 0 entonces {d0 , . . . , dm+1 } es una base de Km+1 (A, r0 ) por ser A−ortogonales y por tanto linealmente independientes. 

ii) rm+2 ⊥ d` ,

∀` ≤ m + 1

Para ` = m, m + 1 es cierto por construcci´on (v´ease Lema 5.7). Para el resto de valores ` ≤ m − 1, utilizamos rm+2 = rm+1 − ξm+1 Adm+1 .

Por inducci´on, rm+1 ⊥ d` , mientras que para el otro t´ermino observamos que (Adm+1 ) ⊥ d`

⇐⇒

dm+1 ⊥A d` ,

y ´esto es lo que acabamos de probar en el apartado anterior.

iii) rm+2 ⊥ r` ,



∀` ≤ m + 1.

Tomemos ` ≤ m. Entonces rm+2 ⊥ r`

⇐⇒ ⇐⇒

(rm+1 − ξm+1 Adm+1 ) ⊥ r` ⇐⇒ (Adm+1 ) ⊥ r` (dm+1 ) ⊥A r` .

donde hemos aplicado la hip´otesis de inducci´on en el segundo paso. Ahora, como r` ⊂ K` (A, r0 ), por el punto i) podemos escribir r` = β0 d0 + β1 d1 + . . . + β` d` .

(5.6)

El resultado se sigue de la propiedad i) ya que dm+1 ⊥A dk para k ≤ m. Finalmente, si rm+1 6= 0 entonces {r0 , . . . , rm+1 } es una base de Km+1 (A, r0 ) por ser ortogonales.  100

´ II LECCION

Cap´ıtulo 5. Matrices sparse en Matematicas. Metodos iterativos

Un examen m´as cuidadoso de la demostraci´on anterior comprueba que ´esta falla en el caso de que en un paso rm+1 ´o dm+1 sean nulos. En cualquiera de estos casos Km (A, r0 ) = Km+1 (A, r0 ).

r do rra Bo

Ahora bien esto sucede si y s´olo si ha habido convergencia en el paso m (si dm+1 = 0 y por tanto rm = 0) o en el paso m + 1 (si rm+1 = 0). Esto es, si la direcci´on de descenso es la nula simplemente es porque ya hemos alcanzado la soluci´on, y viceversa, si el residuo es nulo, la direcci´on de descenso para la siguiente iteraci´on es la nula. Notas finales

El Gradiente Conjugado fue propuesto por Magnus R. Hestenes y Eduard Stiefel en 1952. Lo m´as curioso es que el m´etodo fue desarrollado de forma independiente por estos nos que dos autores. Seg´ un cuenta Marvin Stein13 , un estudiante postdoctoral en aquellos a˜ program´o el algoritmo por primera vez para Hestenes, Stiefel coincidi´o con Hestenes en una conferencia en UCLA (University of California, Los Angeles) y le coment´o a grandes trazos el m´etodo en el que estaba trabajando. Stiefel estaba impresionado sobre las buenas propiedades que mostraba este m´etodo hasta que revisando las tarjetas perforadas que conten´ıan el programa implementado cay´o en la cuenta de que se trataba del mismo m´etodo sobre el que independiente ´el estaba trabajando14 . Hemos visto que el m´etodo del Gradiente Conjugado es un m´etodo directo, en tanto en cuanto da la soluci´on en un n´ umero finito de pasos, concretamente n, el n´ umero de filas de la matriz. Sin embargo, se programa como un m´etodo iterativo, de forma que se busca la convergencia en muchas menos iteraciones. En cada iteraci´on se tiene la estimaci´on !m p κ(A) − 1 ke0 kA kem+1 kA ≤ 2 p κ(A) + 1

donde de nuevo em := xm − x es el error en el paso m−´esimo y e0 el error inicial. El resultado anterior es algo incompleto pero sirve para hacer patente la sensibilidad del m´etodo ante el condicionamiento de una matriz que, aunque menor que en el caso del m´etodo del Gradiente (por la ra´ız cuadrada), sigue siendo importante. Si la matriz tiene un condicionamiento moderado, el m´etodo del Gradiente Conjugado dar´a una soluci´on aceptable en unas pocas iteraciones. Sin embargo, esto no suele ser un caso habitual. Las matrices que surgen en la resoluci´on de ecuaciones en derivadas parciales, por ejemplo elementos o vol´ umenes finitos, suelen ser, adem´as de matrices sparse, mal condicionadas, por lo que el m´etodo del Gradiente Conjugado requiere de bastantes iteraciones15 . Estas razones hicieron que el Gradiente Conjugado se tomara como un m´etodo m´as, sin concederle especial relevancia y confundi´endose con la multitud de m´etodos para la resoluci´on de sistemas de ecuaciones lineales que iban surgiendo a su alrededor. Esta 13 An´ecdota recogida por Yousef Saada y Henk A. van der Vorstb en “Iterative solution of linear systems in the 20th century” publicado en “Journal of Computational and Applied Mathematics” en el a˜ no 2000. 14 Esta coincidencia no es de todas formas un caso aislado en las Ciencias en general y en las Matem´aticas en particular. En ocasiones parece como si las ideas estuviesen flotando en el ambiente a la espera de que alguien diera el paso final de plasmarlas. 15 O(n1/3 ) en problemas en 3D, O(n1/2 ) en 2D es un comportamiento t´ıpico.

101

´ II LECCION

5.2 M´etodos iterativos para sistemas lineales

situaci´on se prolong´o durante casi 20 a˜ nos hasta que las ideas del precondicionamiento cambiaron radicalmente esta situaci´on y encumbraron al Gradiente Conjugado a su posici´on actual16 . El precondicionamiento consiste, a grandes rasgos, en cambiar el sistema por uno equivalente17

r do rra Bo Ax = b,

−1 −> −1 L | AL {z } y = L | {z b}, c B

x = L−> y

y aplicar el m´etodo al sistema By = c. Para su implementaci´on basta con conocer simplemente la matriz producto M = LL> que recibe el nombre de precondicionador de A. En general, la matriz L−1 AL−> no se construye, porque el producto por el precondicionador hace que se pierdan algunas de las buenas propiedades de la matriz original. Ahora bien, y he aqu´ı la ventaja del m´etodo, s´ olo necesitamos calcular productos por M −1 , que se reducen sistemas lineales con M como matriz de coeficientes. Obviamente, y de forma similar a como proced´ıamos con la descomposici´on de Cholesky, esto equivale resolver dos sistemas lineales con L y L> . La buena noticia es que es posible construir matrices para las que estos sistemas son f´aciles de resolver. Por ejemplo, L puede ser sparse y triangular. El m´etodo del Gradiente Conjugado rara vez se programa sin precondicionar. De hecho, el comando de Matlab con el Gradiente Conjugado implementado es pcg de preconditioned conjugate gradient. En u ´ltima medida, el ´exito del Gradiente Conjugado origin´o el nacimiento de una familia entera de m´etodos, los conocidos como m´ etodos de Krylov, que trataban de extender las buenas propiedades del m´etodo a matrices m´as generales. Por ejemplo, BiCG, BiCGSTAB, CGS, QMR, GMRES, MINRES, etc. Algunos de estos m´etodos requieren que la matriz sea sim´etrica y otros son v´alidos para matrices arbitrarias. Un precondicionador universal, es v´alido en muchos casos, es la descomposici´on de Cholesky incompleta. Va m´as all´a de los contenidos de este curso describir detalladamente en qu´e consiste pero podemos dar una idea. Se trata de, grosso modo, aplicar el m´etodo de Cholesky pero restringiendo la creaci´on de nuevas entradas. El resultado es una matriz L tal que LL> ≈ A en alg´ un sentido. Por tanto, L−1 AL−> ≈ In y su condicionamiento es moderado, o al menos mejor que el de A. En Matlab se encuentra implementada en el comando cholinc. El siguiente ejercicio ilustra el efecto del precondicionamiento en la convergencia del Gradiente Conjugado y con ello trata de convencer de la necesidad de utilizarlo en la resoluci´on de (muy) grandes sistemas de ecuaciones. Ejercicio 5.17 Las siguientes instrucciones

>> [p,e,t]=initmesh(’lshapeg’,’Hmax’,0.05); >> [a,b]=assempde(’lshapeb’,p,e,t,1,0,1);

devuelven en a una matriz sparse sim´etrica definida positiva proveniente de resolver la ecuaci´on de Poisson (una ecuaci´on en derivadas parciales) por el m´etodo de elementos finitos en un 16

La American Mathematic Society lo sit´ uo entre los diez algoritmos m´as relevantes del siglo XX, junto con, por ejemplo, la Transformada R´ apida de Fourier (FFT) o el algoritmo QR para el c´alculo de valores y vectores propios. 17 Utilizamos la notaci´ on L−> = (L−1 )> , es decir invertir y trasponer (o equivalentemente, trasponer e invertir).

102

´ II LECCION

Cap´ıtulo 5. Matrices sparse en Matematicas. Metodos iterativos

Metodo del gradiente

0

10

sin precondicionar precondicionado −1

10

r do rra Bo −2

10

−3

10

−4

10

Residuo

−5

10

−6

10

−7

10

−8

10

0

50

100

150

200

250

Iteraciones

Figura 5.5: Efecto del en el Gradiente Conjugado.

dominio en forma de ‘L’. La matriz tiene aproximadamente 2100 filas con 14500 elementos no nulos18 . Con el comando spy se puede ver la forma de a, su tama˜no y el n´umero de entradas no nulas. Aplica el comando pcg que contiene implementado el Gradiente Conjugado. Por ejemplo, con >>[x,flag, relres,iter,resvec] = pcg(a,b,1e-7,100);

aplicas el m´etodo con una tolerancia relativa de 10−7 y un n´umero m´aximo de 100 iteraciones. En relres se recoge el residuo relativo de la soluci´on calculada (kb − Axk/kbk), en resvec un historial del residuo en cada paso y en flag una variable que informa sobre qu´e ha sucedido en la aplicaci´on del m´etodo. As´ı flag==1 indica que se ha alcanzado el n´umero m´aximo de iteraciones sin convergencia, mientras que si flag==0 entonces ha habido convergencia. Para ver el historial de la convergencia del m´etodo se puede ejecutar >> semilogy(resvec);

Observa que es necesario o aumentar el n´umero de iteraciones m´aximas o disminuir la tolerancia para obtener convergencia. A continuaci´on vamos a utilizar un precondicionador muy sencillo basado en la descomposici´on de Cholesky incompleta. Teclea >> R=cholinc(a,’0’);

De nuevo, con los comandos habituales puedes ver tanto la forma como el n´umero de entradas no nulas de R. Modificando las instrucciones anteriores con 18

Por cierto, el logo de Matlab es la soluci´on de un problema de este tipo.

103

5.2 M´etodos iterativos para sistemas lineales

´ II LECCION

>>[x2,flag2, relres2,iter2,resvec2] = pcg(a,b,[],100,R’,R); est´as aplicando el m´etodo del Gradiente Conjugado precondicionado con R> R. ¿Disminuye el n´umero de iteraciones? (ver iter2). ¿Y el tiempo de c´alculo?. ¿Puedes ser ahora m´as exigente con la tolerancia?.

r do rra Bo Ejercicio 5.18 Con la orden helpwin lee la ayuda que proporciona Matlab para pcg. ¿Qu´e otros m´etodos iterativos est´an implementados?. Consulta tambi´en la ayuda de cholinc y luinc.

104

r do rra Bo Lecci´on III

Funciones como argumento. Recursividad F´ormulas de cuadratura. FFT

105

r do rra Bo

r do rra Bo

Introducci´ on

Hobbes clearly proves that every creature Lives in a state of war by nature; So naturalists observe a flea Has smaller fleas that on him prey, And these have smaller still to bite’em, And so proceed ad infinitum. Swift, Poetry: a Rhapsody

En esta lecci´on abordaremos dos nuevos aspectos de Matlab: el env´ıo de funciones como argumentos de otras funciones y la recursividad, esto es, la habilidad de que las funciones se llamen a s´ı mismas. Adem´as mostraremos una forma alternativa de definir funciones en la ventana de comandos. En la segunda parte hablaremos de las reglas de cuadratura cl´asicas para la aproximaci´on de integrales y veremos una implementaci´on sencilla de un m´etodo de integraci´on adaptativa. Finalizaremos con la transformada discreta de Fourier, y su c´alculo mediante la transformada r´apida de Fourier (FFT). La implementaci´on de estos algoritmos servir´a de ilustraci´on de las estrategias de recursividad, que sirven para obtener un c´odigo simple y legible.

107

r do rra Bo

108

r do rra Bo

Cap´ıtulo 6

Matlab: Funciones como argumentos. Recursividad 6.1.

Funciones inline

En la secci´on 3.2 de la Lecci´on I mostramos la definici´on de funciones mediante ficheros de texto (con extensi´on *.m). Existe una forma alternativa de introducir funciones en Matlab que puede utilizarse directamente en la l´ınea de comandos o en el c´odigo de una funci´on. Por ejemplo, >> f=inline(’exp(-x)*sin(x)’,’x’);

define la funci´on f (x) = e−x sen(x). Para evaluar se procede igual >> f(2) ans =

0.1231

A efectos pr´acticos, inline es equivalente a editar una funci´on con nombre “f” y a escribir el correspondiente c´odigo. La definici´on queda en memoria pero una vez cerrada la sesi´on ´ de Matlab (esto es, al salir del programa) la funci´on se pierde. Esta es pues una importante 1 desventaja frente la funciones basada en m-files . Sin embargo puede resultar u ´til para tareas sencillas tanto en el modo comando como en el c´odigo de una subrutina. Nada impide definir funciones con m´as argumentos, >> g=inline(’x*cos(y)-y*cos(x)’,’x’,’y’);

Los u ´ltimos argumentos del comando inline definen las variables de la funci´on. Si no se especifican, Matlab trata de reconocer cu´ales son las variables y las ordena alfabeticamente: 1

En el men´ u, seleccionando File → Save workspace as se pueden grabar las variables y funciones utilizadas en la sesi´ on actual de Matlab. Otra posibilidad es utilizar la orden save indicando que queremos grabar f . En cualquier caso, ambas opciones no son muy naturales.

109

´ III LECCION

6.1 Funciones inline >> g=inline(’x^2*cos(y)-y*cos(x)*z’); >> g g =

r do rra Bo

Inline function: g(x,y,z) = x^2*cos(y)-y*cos(x)*z

De todas formas, expresar todas las variables expl´ıcitamente puede aclarar y facilitar la lectura, adem´as de especificar el orden de las variables en la definici´on de la funci´on: >> f=inline(’x*cos(k*x)’) f =

Inline function: f(k,x) = x*cos(k*x)

>> f=inline(’x*cos(k*x)’,’x’,’k’) f =

Inline function: f(x,k) = x*cos(k*x)

Las funciones anteriores no est´an vectorizadas, es decir, al aplicarlas sobre un vector o matriz no act´ uan elemento a elemento. Para ello, deber´ıa escribirse >> g = inline(’x.^2.*cos(y)-y.*cos(x).*z’); >> g([0 pi 0],[pi 0 0], [0 0 pi]) % funcion vectorizada ans = 0

9.8696

0

Otra forma, m´as sencilla, es introducir la funci´on de la forma habitual y pedir luego a Matlab que la prepare para su aplicaci´on a vectores. El comando dedicado a esta tarea es vectorize: >> g = inline(’x^2*cos(y)-y*cos(x)*z’) % funcion sin vectorizar g =

Inline function: g(x,y,z) = x^2*cos(y)-y*cos(x)*z

>> g= vectorize(g)

110

´ III LECCION

Cap´ıtulo 6. Matlab: Funciones como argumentos. Recursividad

g = Inline function: g(x,y,z) = x.^2.*cos(y)-y.*cos(x).*z

r do rra Bo

Observa que tras la aplicaci´on de este comando, Matlab redefine la funci´on a˜ nadiendo “.” en los sitios adecuados.

6.2.

Funciones como argumentos

Es frecuente que en programaci´on m´as avanzada se requiera que las funciones trabajen sobre funciones. Por ejemplo, podemos plantearnos implementar una funci´on que realice la siguiente tarea dada una funci´on de una variable y dos valores dibujar la funci´on entre esos valores

En este caso, uno de los argumentos es la funci´on a dibujar. Veamos c´omo se ha implementado 01 02 03 04 05 06 07 08 09 10 11 12 13 14 15 16 17 18 19 20 21 22

% MIPLOT % % MIPLOT(F,A,B) % MIPLOT(F,A,B,N) %

Dibuja la funcion F entre A y B Toma N puntos entre A y B

function miplot(f,a,b,varargin)

if nargin3 n=varargin{1}; else n=200; end

x=linspace(a,b,n); % vector con n puntos entre a y b y=feval(f,x); % f debe estar vectorizada plot(x,y) return

En la l´ınea 07, f recoge la funci´on argumento, mientras que en 20 se procede a evaluar ´esta mediante feval Para enviar la funci´on existen dos posibilidades: 111

´ III LECCION

6.2 Funciones como argumentos Si enviamos una funci´on inline, basta con insertar su nombre >> fun=vectorize(inline(’exp(-x)*cos(4*x)’)); >> miplot(fun,0,2*pi,200)

r do rra Bo

Si la funci´on es propia de Matlab o est´a implementada en un fichero m-file en la carpeta de trabajo (o en alguna accesible), podemos • utilizar “@”2

>> miplot(@sin,0,2*pi,200)

• indicar el nombre de la funci´on entre comillas >> miplot(’sin’,0,2*pi,200)

Nota. La funci´on plot dibuja el vector y versus x. Concretamente, por defecto construye el pol´ıgono con v´ertices(x(i),y(i)). Si se toma un n´ umero suficiente de puntos esto basta para obtener una buena gr´afica. Este comando es una de las salidas gr´aficas m´as simples de Matlab y admite una amplia variedad de argumentos opcionales que controlan el aspecto final del dibujo. En una lecci´on posterior (Lecci´on V) veremos este comando y otros relacionados con las salidas gr´aficas. 

Ejercicio 6.1 Modificar el programa miplot para que en caso de no recibir los argumentos a y b los pida por pantalla.

(Ayuda. La orden input lee datos por pantalla tras mostrar un mensaje. Necesitar´as que ahora a y b pasen a ser argumentos opcionales.)

Ejercicio 6.2 Lee la ayuda de Matlab sobre plot. Ensaya diferentes variantes, observa como se puede cambiar de forma sencilla tanto la forma de la gr´afica (l´ınea continua, l´ınea a trozos, raya-punto, s´olo puntos,...), el color,...

6.2.1.

Recursividad

Un aspecto ya habitual en muchos lenguajes de programaci´on es la recursividad, es decir, la habilidad de que una funci´on se llame a s´ı misma. Es habitual su utilizaci´on cuando se programan estrategias de tipo divide y vencer´ as, que consiste, a grandes trazos, en dividir un problema en problemas iguales pero de menores dimensiones. Quiz´as el ejemplo m´as sencillo (y cl´asico) se basa en la funci´on factorial. n! = n · (n − 1) · · · 1.

De una manera simple, podemos definir de forma recursiva  n · (n − 1)!, si n > 0, n! = 1, si n = 0.

Su implementaci´on en Matlab es ahora tan sencilla como sigue

2

Matlab recomienda esta forma. El operador @ accede al handle de la funci´on que es la referencia que tiene Matlab de la funci´ on. Para mayor informaci´on, ver helpwin function handle.

112

´ III LECCION 01 02 03 04 05 06 07 08 09 10 11 12 13 14 15 16

Cap´ıtulo 6. Matlab: Funciones como argumentos. Recursividad

% FACT % % FACT(N) devuelve n! %

r do rra Bo

function f=fact(n)

if (n> f=inline(’x*cos(x)’); f=vectorize(f);

La integral exacta se puede calcular tomando un n´umero muy elevado de puntos (por ejemplo n = 10000) con la regla de Simpson, que es la de mayor precisi´on. Mide el error para diferentes valores de n y observa como decrece el error. Una buena elecci´on podr´ıa ser n = 10, 20, 40, 80, ..., esto es, multiplicando por 2 el n´umero de puntos. Deber´ıas observar que para funciones suaves el error se divide por 4 o por 16, seg´un la regla que se aplique. Testa los programas con los siguientes ejemplos i) f1 (x) = x cos(x) en [0, π]

ii) f2 (x) = xe−x en [0, 3]

iii) f3 (x) = x log(x) en [1, 2] y en [0, 2]9

iv) f4 (x) = cos2 (x) en [0, π/2], en [0, π] y en [0, 2π].

Un fichero script te puede venir bien para este ejercicio. ¿Qu´e observas con las reglas del trapecio y del punto medio en el u´ltimo caso?.

Nota. En esta serie de experimentos se observa que la regla de Simpson no alcanza el orden que la teor´ıa predice en el ejemplo iii) sobre el intervalo [0, 2]. Ello es debido a que las derivadas de la funci´on tienen una singularidad en el origen. Menos simple de explicar es la superconvergencia (convergencia mejor de lo esperado) R 2π 2 que se observa para 0 cos (x) (punto iv)).Esto es consecuencia de que el integrando, adem´as de regular, es π−peri´odico y se est´a integrando en un m´ ultiplo de su intervalo de periodicidad. En una secci´on posterior daremos una explicaci´on a este fen´omeno tan sorprendente.  Ejercicio 7.10 Implementa la regla compuesta de 3/8, la siguiente a la regla de Simpson, que aparec´ıa en el Ejercicio 7.6. Compara los resultados con la regla de Simpson. ¿Qu´e observas? 9

En este caso, evaluar en 0 es una singularidad de tipo 0 · ∞. En realidad el l´ımite cuando x → 0 es cero, que se puede tomar como valor de f (0). Una forma de evitar este problema es aplicar la f´ormula en [, 2] con  1 y C independiente de r y de n, con lo que el orden es de hecho exponencial. 

Ejercicio 7.12 Comprueba que si aplicas un paso de extrapolaci´on a la f´ormula del trapecio compuesta obtienes el m´etodo de Simpson. Ejercicio 7.13 Implementa la extrapolaci´on de Richardson, seg´un el siguiente prototipo de funci´on 01 02 03 04 05 06 07

% RICHARDSON % % V= RICHARDSON(F,A,B,N,M) Aplica la formula del trapecio con N, 2*N,4*N,..., 2^(M-1)*N puntos Construye la matriz de extrapolacion V M x M donde V(:,i) es el resultado de aplicar el paso i-1 de Richardson.

Ejercicio 7.14 Existe una forma m´as general de definir la extrapolaci´on. Para ello precisamos que las sucesivas h decrezcan de una forma proporcional α0 (h),

α0 (rh),

α0 (r2 h), . . . , α0 (rn h).

En el caso expuesto, r = 1/2. ¿C´omo se adapta la extrapolaci´on para otras elecciones de r ∈ (0, 1)?.

7.1.6.

Integraci´ on adaptativa

Las f´ormulas anteriores adolecen de un importante defecto: todas asumen que el comportamiento de la funci´on es m´as o menos uniforme en todo el intervalo de integraci´on. La situaci´on usual es que la funci´on tenga zonas donde var´ıa de forma brusca y zonas donde su comportamiento sea considerablemente m´as suave. Intuitivamente, se entiende que las primeras zonas son las m´as problem´aticas. El siguiente paso en cualquier algoritmo num´erico es dise˜ nar m´etodos adaptativos. Estos esquemas reconocen aquellas zonas que requieren mayor trabajo (refinar, en la terminolog´ıa habitual) y aqu´ellas donde basta unas pocas evaluaciones para obtener una aproximaci´on suficientemente buena. Para abordar esta tarea debemos disponer en primer lugar de un buen estimador del error, esto es, de un postproceso que nos de informaci´on sobre el error que estamos cometiendo y que as´ı permita dilucidar qu´e partes del intervalo de integraci´on requieren mayor esfuerzo y cu´ales no. 13

Concretamente que la funci´ on sea anal´ıtica

129

´ III LECCION

7.1 F´ormulas de cuadratura

r do rra Bo Zona regular

Zona Irregular

Zona regular

Figura 7.4: Integraci´on adaptativa

A continuaci´on expondremos una implementaci´on muy sencilla de una integraci´on adaptativa basada en la regla de Simpson. El estimador se basa en comparar el resultado obtenido, en cada subintervalo, por la regla de Simpson simple, y la compuesta con dos subintervalos. Dado que la regla de Simpson se obtiene de la regla del trapecio utilizando un u ´nico paso de extrapolaci´on (Ejercicio 7.12), obtenemos de (7.3) Z

b

f (s) ds −

a

 h (1) f (a) + 4f (c) + f (b) = c2 h4 + O(h6 ) |6 {z }

(7.4)

Q1 (f )

Z

b

f (s) ds −

a

(1)  c h f (a) + 4f (d) + 2f (c) + 4f (e) + f (b) = 2 h4 + O(h6 ) (7.5) 16 {z } |12

Q2 (f )

donde h = (b − a), c es el punto medio de (a, b), d y e, los puntos medios de (a, c) y (c, b). (1) El t´ermino dominante del error, para h suficientemente peque˜ no, es c2 h4 de forma que Z

b

(1)

f (s) ds − Q1 (f ) ≈ c2j h4 .

a

A priori este t´ermino no puede ser calculado, pero puede ser despejado de (7.4) y (7.5), sin m´as que sustraer a la primera identidad la segunda. As´ı obtenemos  (1) 4 1 Q2 (f ) − Q1 (f ) ≈ 1 − 16 c2j h

y por tanto

16 (1) (Q2 (f ) − Q1 (f )) ≈ c2j h4 ≈ 15

Z a

| 130

b

f (s) ds − Q1 (f ) . {z } error

´ III LECCION

Cap´ıtulo 7. F´ormulas de cuadratura. FFT

La idea de nuestro esquema adaptativo es la que sigue: dado un intervalo [a, b] y una tolerancia ε

r do rra Bo

Calculamos Q2 (f ) y Q1 (f ) como antes, y 16 est = (Q1 (f ) − Q2 (f )) 15

Si est < ε el resultado se considera bueno y se devuelve Q2 (f );

Si est > ε se aplica el argumento anterior en los subintervalos [a, c] y en [c, b] con una tolerancia de /2 y se devuelve como integral la que calculada en [a, c] y en [c, b]

Hay por lo tanto un proceso de subdivisi´on de los intervalos, de manera que la u ´nica forma, en este estado inicial, de que un subintervalo no se divida es que la integral se calcule dentro de la tolerancia prefijada. Obviamente el algoritmo anterior se programa de forma natural de manera recursiva. El papel fundamental lo juega una funci´on, que podr´ıa seguir el siguiente prototipo simpsonadaptativo(f,a,c,b,fa,fc,fb,integ,tol)

donde f es la funci´on a integrar, a y b son los extremos de integraci´on, c el punto medio, fa, fb y fc los valores de f en a, b y c, integ es el resultado de aplicar la regla de Simpson en [a,b] y tol la tolerancia con la que se pide la integral. Se procede entonces siguiendo los siguientes pasos 1. Se toma h=(b-a), d=(a+c)/2, e=(c+b)/2 y se calcula fd = f (d) y fe = f (e) 2. Se calcula

integ21 = h/12*(fa + 4fd + fc) integ22 = h/12*(fc + 4fe + fb) integ2 = integ21 + integ22

3. Se calcula el estimador

16 est = (integ − integ2) 15

4. Si esttol entonces se calcula

integ21 = simpsonadatativo(f, a, d, c, fa, fd, fc, integ21, tol/2) integ22 = simpsonadatativo(f, c, e, b, fc, fe, fb, integ22, tol/2) integ = integ21 + integ22. 131

´ III LECCION

7.1 F´ormulas de cuadratura

r do rra Bo

Si hemos seguido el esquema anterior y nos vemos forzados a dividir en dos subintervalos, habremos evaluado ya f en a, c y en su punto medio d y en c, b y el correspondiente punto medio e. Tambi´en se habr´a calculado la regla de Simpson en estos intervalos. Es por ello que enviamos todos estos valores en las llamadas de la funci´on simpsonadaptativo, dado que generalmente la operaci´on m´as costosa es precisamente evaluar la funci´on. Notemos que se ha optado por devolver como aproximaci´on de la integral Q2 (f ), en lugar de Q1 (f )14 . Otra variante es devolver 16Q2 (f ) − Q1 (f ) 15

que es el primer paso de extrapolaci´on de Simpson (o el segundo del trapecio, de acuerdo al problema 7.2). La forma m´as simple de implementar el proceso anterior es introduciendo una funci´on de cabecera que prepare los datos iniciales: recibe la funci´on, el intervalo de integraci´on y la tolerancia solicitada, y calcula para arrancar la subrutina simpsonadaptativo el punto medio c, los valores de f en a, b y c y el resultado de aplicar la regla de Simpson simple en [a, b]. Por ejemplo 01 02 03 04 05 06 07 08 09 10 11 12 13 14 15 16 17

% % % % % % %

SIMPSONRECURSIVO

INTEG= SIMPSONRECURSIVO (F,A,B,TOL)

Devuelve una aproximacion de la integral mediante una integracion adaptativa basada en la regla de Simpson con tolerancia TOL

function integ=simpsonrecursivo(f,a,b,tol)

c=(a+b)/2; fa=feval(f,a); fb=feval(f,b); fc=feval(f,c); integ=(b-a)*(fa+4*fb+fc)/6; %regla de Simpson integ=simpsonadaptativo(f,a,c,b,fa,fc,fb,integ,tol); return

Resta por programar la funci´on simpsonadaptativo, trabajo que proponemos al lector. Ejercicio 7.15 Implementa la regla de Simpson adaptativa.

Ejercicio 7.16 El m´etodo tal como est´a programado puede entrar en un bucle infinito si no se consigue integrar con la tolerancia exigida en las sucesivas subdivisiones de un intervalo. Para evitar este problema hacemos que el programa lleve control del n´umero de veces que ha subdividido un intervalo. La funci´on puede seguir la siguiente sintaxis 14

Casi nadie dudar´ıa en esta elecci´ on. Es decir, es esperable que Q2 (f ) sea mejor que Q1 (f ), as´ı que ¿por qu´e no devolver lo mejor que se tiene?. Matem´aticamente, sin embargo, el estimador del error controla el error de Q1 (f ) y no de Q2 (f ).

132

´ III LECCION

Cap´ıtulo 7. F´ormulas de cuadratura. FFT

1.5

r do rra Bo 1

0.5

0 0

0.2

0.4

0.6

0.8

1

1.2

1.4

1.6

1.8

Figura 7.5: Integraci´on adaptativa de



2

x

[integ,subd2]=simpsonadaptativo(f,a,c,b,fa,fc,fb,integ,tol,subd)

donde subd2=subd+1. Si subd2 > subdmax se devuelve un mensaje de error, se deja de subdividir y se continua la ejecuci´on del programa devolviendo el u´ltimo valor calculado. El par´ametro subdmax puede dejarse como un valor por defecto que puede modificarse si el usuario especifica otro valor. Es decir, entra a formar parte de un conjunto variable de argumentos de entrada. Implementa el m´etodo resultante. Ejercicio 7.17 Por u´ltimo podemos llevar un control sobre los puntos que hemos evaluado. Para ello basta utilizar [integ,subd2,x2]=simpsonadaptativo(f,a,c,b,fa,fc,fb,integ,tol,subd,x)

con x2=[x d e] donde d y e son los puntos medios de [a,c] y [c,b] respectivamente. Implementa el m´etodo resultante.

(Ayuda: si al final se desea que los puntos x2 est´en ordenados se puede aplicar la instrucci´ on sort(x2) que devuelve el vector con sus componentes ordenadas de menor a mayor.)

Nota final

De un estimador se suele hablar de dos conceptos bien importantes: confiabilidad y eficiencia. Un estimador es confiable si efectivamente el error est´a por debajo de lo que el estimador calcula. Por contra, es eficiente si el estimador aproxima bien el error cometido. Nuestro estimador, en general, es poco eficiente: el error real suele estar muy por debajo de la cantidad que nos devuelve el√estimador, especialmente si el intervalo de integraci´on es grande. Por ejemplo, para f = x e integrando en [0, 2], se observa que con una tolerancia 133

´ III LECCION

7.2 Transformada r´apida de Fourier

Adaptativa Error neval 8.91e−03 7 1.41e−04 15 1.57e−06 29 2.12e−07 47 8.48e−09 77 2.64e−10 133 8.27e−12 233 2.25e−13 421

Error 8.01e−3 2.70e−3 1.03e−3 5.01e−4 2.45e−4 1.09e−4 4.73e−5 1.96e−5

Trapecio

Simpson

Error −3.67e−2 −1.06e−2 −3.81e−3 −1.82e−3 −8.67e−4 −3.81e−4 −1.64e−4 −6.76e−5

Error −1.01e−2 −3.59e−3 −1.40e−3 −6.90e−4 −3.33e−4 −1.36e−4 −6.41e−5 −2.65e−5

r do rra Bo

tol 10−1 10−2 10−3 10−4 10−5 10−6 10−7 10−8

Pto. medio

R2√ umero de Cuadro 7.2: Resultados num´ericos para 0 x dx. Tolerancia exigida (tol), n´ evaluaciones (neval) y error cometido (Error). Comparativa con las reglas del punto medio, del trapecio y de Simpson con h fijo y el mismo n´ umero de evaluaciones

de 10−5 el error real cometido por el m´etodo adaptativo es 8.48 · 10−9 , un error 1000 veces menor en magnitud. Una forma de corregir este problema es, una vez que se ha decidido dividir el intervalo de integraci´on en dos subintervalos, no exigir una tolerancia tol/2 en cada uno de ellos, sino utilizar r ∗ tol con r ∈ [1/2, 1]. Matlab utiliza de hecho r = 1. Matlab cuenta con algunas funciones encargadas de la integraci´on num´erica: quad

quadl

dblquad

triplequad

Las dos u ´ltimas aplican reglas de cuadratura para integrales dobles y triples respectivamente. El comando quad implementa esencialmente el m´etodo de Simpson recursivo que hemos visto en esta secci´on. Por otro lado, quadl utiliza una regla de orden mayor que da mejores resultados si el integrando es m´ as regular. El c´odigo de estas funciones est´a abierto, luego se puede editar para ver los detalles de su implementaci´on.

7.2.

Transformada r´ apida de Fourier

La transformada r´apida de Fourier, o FFT, seg´ un sus siglas en ingl´es15 , es una herramienta muy potente en el an´alisis de se˜ nales peri´odicas y cuyas aplicaciones se han extendido a aspectos muy diferentes del C´alculo Num´erico. Existen diversas formas de introducir la FFT. Hemos escogido la interpretaci´on que relaciona la transformada de Fourier discreta con los coeficientes de Fourier para enlazar seguidamente con algunas aplicaciones. 15

El nombre correcto ser´ıa transformada discreta r´apida de Fourier, para distinguirla de la transformada de Fourier continua. Sus siglas en ingl´es, FFT, podr´ıan entonces provenir de Fast Fourier Transform o Finite Fourier transform. De acuerdo a lo anterior, las siglas m´as adecuadas ser´ıan FFFT (Fast Finite Fourier transform), pero nadie utiliza esta nomenclatura, seguramente por el exceso de Fs)

134

´ III LECCION

Cap´ıtulo 7. F´ormulas de cuadratura. FFT

Parte de esta secci´on, especialmente la referente a la transformada r´apida de Fourier, se ha obtenido del libro Numerical Computing with Matlab, de Cleve Moler.

7.2.1.

Transformada de Fourier discreta

r do rra Bo

Nota En esta secci´on seguiremos la notaci´on de Euler exp(iθ) = eiθ = cos θ + i sen θ,

θ ∈ R,

donde i es la unidad imaginaria.  Dada una funci´on 1–peri´odica, ´esta se puede expresar en forma de serie de Fourier X

f (θ) =

fb(m) exp(2πimθ),

θ∈R

(7.6)

m∈Z

donde fb(m) es el coeficiente m-´esimo de Fourier 1

Z

m ∈ Z.

f (θ) exp(−2πimθ)dθ,

fb(m) =

0

La convergencia de la serie es un asunto algo delicado16 , pero si la funci´on tiene, por ejemplo, derivada continua, la convergencia de la serie es uniforme: s X fb(m) exp(2πimθ)| → 0, m´ax f (θ) −

θ∈[0,1]

cuando r, s → ∞,

m=−r

lo que en particular justifica alguna de las manipulaciones que haremos a continuaci´on. La identidad (7.6) se interpreta en el sentido de que la funci´on original f es suma infinita de unas frecuencias fundamentales. Observa que para cada m, exp(2πimθ),

es una funci´on 1/m-peri´odica, o dicho de otra forma, su periodo es 1/m (ver la Figura 7.6). Adem´as se tiene la relaci´on Z

∞ X

1

2

|f (θ)| dθ =

0

|fb(m)|2

(7.7)

m=−∞

que se interpreta como que la energ´ıa de funci´on original f es igual a la energ´ıa del vector infinito (. . . , fb(−2), fb(−1), fb(0), fb(1), fb(2), . . .)> . 16

Mucho se ha escrito sobre esto. En cualquier caso hay que especificar en qu´e sentido converge la serie. El sitio m´ as adecuado, matem´ aticamente hablando, es el espacio de las funciones cuyo cuadrado es integrable, que se denota por L2 (0, 1). F´ısicamente se interpreta como el espacio de las se˜ nales cuya energ´ıa es finita.

135

´ III LECCION

7.2 Transformada r´apida de Fourier

Parte Real e Imaginaria de exp(2π i mθ) para m=1,2,3 Freq.1 periodo 1 Freq 2 periodo 1/2 Freq 3 periodo 1/3

1.5

r do rra Bo 1

0.5

0

-0.5

-1

-0.2

0

0.2

0.4

0.6

0.8

1

1.2

Figura 7.6: Primeras exponenciales trigonom´etricas.

Nota. Utilizando la definici´on de la exponencial trigonom´etrica, podemos expresar f = fb(0) +

∞ X

m=1

(fb(m) + fb(−m)) cos(2πm · ) + | {z } =: αm

∞ X

m=1

i(fb(m) − fb(−m)) sen(2πm · ) | {z }

(7.8)

=: βm

donde αm y βm se pueden calcular de forma alternativa mediante Z 1 Z 1 αm = 2 f (θ) cos(2πmθ) dθ, βm = 2 f (θ) sen(2πmθ) dθ. 0

0

La expresi´on (7.8) puede resultar m´as atractiva que (7.6), especialmente si la funci´on es real puesto que implica trabajar u ´nicamente con cantidades reales, sin parte imaginaria. Sin embargo, tanto el an´alisis como una notaci´on m´as compacta animan a utilizar la exponencial compleja. A´ un es m´as, en lo que sigue podemos suponer que las funciones son complejas (devuelven valores en C) y por tanto se cubre este caso de forma muy natural.  Desde un punto de vista pr´actico, es poco habitual que se pueda (o que se proceda a) evaluar la funci´on en cualquier punto. En lugar de ello se dispone de un muestreo es decir, del valor de la funci´on en una serie de puntos uniformemente distribuidos. As´ı definimos xj =

j , N

j = 0, . . . , N − 1,

se eval´ ua yj := f (xj ) ,

j = 0, . . . , N − 1 136

´ III LECCION

Cap´ıtulo 7. F´ormulas de cuadratura. FFT

y se construye el vector    y= 



y0 y1 .. .

  . 

yN −1

r do rra Bo La primera cuesti´on es

¿Es posible recuperar los coeficientes de Fourier de f a partir de y?

La respuesta obvia es no: si tomamos una cantidad finita de informaci´on es imposible recuperar (salvo en casos triviales) los coeficientes de Fourier, que en u ´ltima media son la funci´on y, por tanto, conllevan una cantidad infinita de informaci´on. Ahora bien, la situaci´on es muy diferente si disponemos de informaci´on a priori sobre la funci´on f . Si una funci´on peri´odica f es regular podemos probar que fb(k) → 0,

|k| → ∞

y de hecho de una forma muy r´apida (ver Ejercicio 7.18), por lo que unos pocos coeficientes pueden ser suficientes para reconstruir la funci´on de forma muy aproximada. Para calcular estos coeficientes utilizamos la regla del trapecio, que como hemos visto en la secci´on anterior converge muy r´apidos para funciones regulares y peri´odicas. Todo lo anterior nos conduce a Z 1 b f (k) := f (θ)exp(−2πikθ) dθ 0

f (1) = f (0) = y0



N −1 i X 1 1 h1 ) + f (0) + f ( Nj ) exp(− 2πijk f (1) N N 2 2 j=1

=

N −1 1 X yj ω jk N j=0



=

donde

 ω := exp − 2πi . N

Lo anterior sugiere construir

N −1 1 X Yk := yj ω jk N j=0

como una aproximaci´on de fb(k). El vector    Y= 

y0 y1 .. .

    

yN −1

recibe el nombre de transformada discreta de Fourier de y que denotaremos por F y = Y. Por tanto F : CN → CN , es decir, transforma vectores de n´ umeros (en principio) complejos en vectores complejos. 137

´ III LECCION

7.2 Transformada r´apida de Fourier

Ejercicio 7.18 Sea f es peri´odica con derivada primera continua, θ=1 Z 1 1 b f (θ) exp(−2πikθ) dθ = − f (θ) exp(−2πikθ) f (k) := 2πki 0 θ=0 | {z } =0

1

r do rra Bo

1 2πki

Z

+

f 0 (θ) exp(−2πikθ) dθ.

0

Demostrar entonces que

C k donde C es independiente de k. ¿De qu´e depende C?. Prueba reiterando este argumento que si f es m´as regular el decrecimiento de fb(k) es m´as acusado. |fb(k)| ≤

Para estudiar la relaci´on entre transformada de Fourier continua y discreta precisamos del siguiente lema

Lema 7.5 Para todo k ∈ Z

N −1  1 X = exp − 2πijk N N j=0

(

1,

k = `N para alg´un ` ∈ Z,

0,

en caso contrario.

Demostraci´on. Tomemos como antes

 . ω := exp − 2πi N

Entonces, la suma anterior es simplemente

N −1 N −1 1 X jk 1 X k j ω = (ω ) . N j=0 N j=0

Si k = `N , es decir, si k es un m´ ultiplo de N , ω k = exp(−2πi`) = 1 y la suma anterior es 1. En caso contrario, teniendo en cuenta que 1 + r + r2 + . . . + rm−1 =

1 − rm 1−r

obtenemos que

N −1 1 1 − (ω N )k 1 X k j 1 1 − (ω k )N (ω ) = = . N j=0 N 1 − ωk N 1 − ωk

Ahora, como ω N = 1, se sigue que la suma anterior es nula.  Utilizando el desarrollo en Fourier de f e intercambiando el orden de los sumatorios17 podemos escribir N −1 N −1 N −1  i  1 X 1 X b hX 1 X 2πijk jk yj ω = f (xj ) exp − N = Yk := exp 2πi(m−k)j f (m) . N N j=0 N j=0 N m∈Z j=0

17

Manipulaciones que deben siempre justificarse y que son v´alidas si, por ejemplo, la funci´on tiene derivada primera continua.

138

´ III LECCION

Cap´ıtulo 7. F´ormulas de cuadratura. FFT

Por el lema anterior, N −1 X

exp



2πi(m−k)j N



 =

j=0

1, 0,

si m = k + `N , en caso contrario,

r do rra Bo

por lo que

Yk =

1 Xb f (k + mN ). N m∈Z

De esta forma, Yk recoge no s´olo el coeficiente k−´esimo de Fourier, sino contribuciones en frecuencias m´as altas, cuya distancia al coeficiente k dista un m´ ultiplo de N . Llegado a este punto, conviene recordar que el decreciemiento r´apido a cero de los coeficientes de Fourier cuando |k| → ∞ sugiere que Yk aproxima bien al coeficiente de Fourier m´ as pr´ oximo a cero y la aproximaci´on mejora muy r´apidamente cuando N → ∞. Es decir,  X b  si 0 ≤ k ≤ N2 f (k)+ fb(k + mN ),     m6=0   {z } |    peque˜ no (7.9) Yk = X  N  b b f (k + mN ), f (k − N )+ si 2 < k < N .     m6 = 0   | {z }   peque˜ no

A la operaci´on que a cada Y le asocia el vector original y se conoce como transformada inversa de Fourier discreta y se denota F −1 Y = y.

Con argumentos similares a los utilizados anteriormente se puede ver que yk :=

N −1 X

Yj exp

2πijk N



,

j=0

obteni´endose as´ı una expresi´on muy similar a la transformada de Fourier. En particular, concluimos que F −1 existe y est´a bien definida.

Nota. En el marco continuo, ten´ıamos que Z 1 fb(m) = f (θ) exp(−2πimθ) dθ, 0

f (θ) =

X

fb(m) exp(2πimθ).

m∈Z

Obs´ervese el paralelismo entre la Transformada de Fourier Discreta, y la integral de la expresi´on superior (la primera es la aproximaci´on discreta de la segunda) y la inversa de la Transformada de Fourier Discreta con la serie de Fourier. Ejercicio 7.19 Prueba la expresi´on dada para la inversa de la transformada discreta de Fourier. 139

´ III LECCION

7.2 Transformada r´apida de Fourier

Ejercicio 7.20 Dado que vamos a calcular aproximaciones de los coeficientes centrales de Fourier, podr´ıamos plantearnos definir Yek =

N −1 X

yj ω jk ,

−N/2 < k ≤ N/2

j=0

r do rra Bo ¿Sabr´ıas ver qu´e relaci´on hay entre Yek e Yk ?.

7.2.2.

C´ alculo de la transformada de Fourier Discreta

Es f´acil dar una expresi´on matricial de la transformada de Fourier discreta en t´erminos de la matriz   1 1 1 ··· 1  1 ω ω2 · · · ω N −1     2 ω4 · · · ω 2(N −1)  W :=  ω = exp − 2πi N ,  1 ω  ...............................  2 1 ω N −1 ω 2(N −1) · · · ω (N −1) Con esta matriz, la relaci´on entre y y su transformada Y se escribe simplemente Y = Fy =

1 W y. N

An´alogamente,

y = F −1 Y = W ∗ Y

donde W ∗ es la matriz adjunta  1 1 1 ··· 1 2 N −1  1 ω ω ··· ω  ∗ 2 4  ω · · · ω 2(N −1) W = 1 ω  ............................... 2 1 ω N −1 ω 2(N −1) · · · ω (N −1)



  ,  

ω = ω −1 = exp

2πi N



La matriz W es una matriz de tipo Vandermonde, que ya surgido anteriormente. Adem´as es casi ortogonal: W ∗ W = N IN

donde IN la matriz identidad de orden N . En resumen, la transformada discreta de Fourier, y su transformada inversa, se reducen a calcular un producto matriz-vector. El costo, en una implementaci´on directa, conlleva la construcci´on de la matriz y realizar el producto. S´olo el producto tiene un costo de orden O(2N 2 ) operaciones (sumas y productos).

Ejercicio 7.21 Construye la matriz W ∗ . Ejercicio 7.22 Implementa la transformada discreta de Fourier. 140

´ III LECCION

Cap´ıtulo 7. F´ormulas de cuadratura. FFT

Soluci´ on. Esta es una implementaci´on que evita construir la matriz W . En su lugar calcula sucesivamente las filas, la multiplica por y para hallar el correspondiente coeficiente y calcula la siguiente fila. De esta forma se reduce la memoria utilizada pero no el n´ umero de operaciones % FT % % Y=ft(y) %

r do rra Bo

01 02 03 04 05 06 07 08 09 10 11 12 13 14 15 16 17 18

devuelve la transformada de Fourier discreta la implementacion es la directa

function Y = ft(y)

y=y(:); % y es columna ahora n=length(y); w=exp(-i*2*pi*(0:n-1)/n); W=ones(1,n); Y=zeros(n,1); for j=1:n Y(j)=W*y; W=W.*w end Y=Y/n; return

Ejercicio 7.23 Implementa la transformada inversa de Fourier. Notas finales

Si f es real,

Re fb(k) = Re fb(−k),

Im fb(k) = −Im fb(−k).

Esta simetr´ıa se extiende a la transformada discreta: si y es real Im y0 = 0,

Re yk = Re yN −k ,

Im yk = −Im yN −k ,

k = 1, . . . , N − 1.

De esta forma, si ignoramos la primera componente, la parte real de Y, respectivamente imaginaria, es sim´etrico, respectivamente antisim´etrico, respecto al punto N/2. Este punto se conoce como el punto de Nyquist. Otra analog´ıa con el marco continuo es que la transformada discreta de Fourier preserva, salvo constante multiplicativa, la norma k · k2 del vector original, esto es, su energ´ıa. Concretamente (comparar con (7.7))

1 1 1 1 (W y)∗ (W y) = 2 y∗ W ∗ W y = y∗ y = kyk22 . (7.10) 2 N N N N Hay una falta de consenso en la definici´on de Transformada de Fourier discreta. Nosotros hemos tomado como definici´on de la transformada y de su inversa las dadas por N −1 N −1 X 1 X jk Yk := yj ω , yk := Yj ω −jk , ω = exp(− 2πi ). N N j=0 j=0 kYk22 = Y∗ Y =

141

´ III LECCION

7.2 Transformada r´apida de Fourier

En Matlab, la transformada de Fourier y su inversa est´an implementadas en fft e ifft. La definici´on que se toma es ligeramente diferente Yk :=

N −1 X j=0

jk

yj ω ,

N −1 1 X Yj ω −jk , yk := N j=0

). ω = exp(− 2πi N

r do rra Bo √ En otros textos se multiplica por 1/ N en ambos sumatorios con el fin de dar un aspecto m´as uniforme (en este caso la norma 2 del vector y de su transformada coinciden). En cualquier caso, la diferencia entre las diferentes transformadas es simplemente el producto por una potencia de N . Todo lo desarrollado en esta secci´on es perfectamente aplicable a funciones peri´odicas con distintos periodos, sin m´as que aplicar un cambio de variables y transformarla en 1−peri´odica.

7.2.3.

Aplicaciones a la eliminaci´ on de ruido

Una de las primeras aplicaciones surge en el an´alisis de se˜ nales y fen´omenos peri´odicos. Vamos a mostrar un (muy) simple ejemplo en la eliminaci´on de ruido de una se˜ nal peri´odica. Suponemos que la se˜ nal, dada por una funci´on regular y suave, es perturbada por un ruido que puede ser modelizado por una variable aleatoria que sigue una distribuci´on uniforme. Como la se˜ nal original es regular, sus coeficientes de Fourier decrecen r´apidamente a cero. En particular, la funci´on puede ser aproximada por una suma parcial con unas pocas exponenciales trigonom´etricas. Dicho de otra forma, la funci´on tiene unas pocas frecuencias importantes mientras que el resto tiene una aportaci´on despreciable. Tomemos por ejemplo una se˜ nal dada por la funci´on f (x) := cos(cos(12πx)) sen(2πx)

En la Figura 7.7 se muestra la funci´on y sus coeficientes de Fourier, que decrecen r´apidamente a cero. Tambi´en se muestra una evaluaci´on en 64 puntos (un muestreo) uniformemente distribuidos y la transformada de Fourier discreta resultante. Obs´ervese la relaci´on entre transformada discreta de Fourier y los coeficientes de Fourier mostrada en (7.7). En el campo discreto, tenemos un ruido r y el vector transformada de Fourier discreta R = F r. Visto en el campo transformado, esta perturbaci´on tiene un tama˜ no, relacionado con la amplitud del ruido y con el n´ umero de puntos que se han tomado de muestra. Dado el comportamiento altamente irregular, es esperable que las contribuciones en todas las frecuencias sean similares. Pero kRk22 =

1 krk22 ≤ m´ax |rj |. j=0,...,N −1 N

Por tanto, si el ruido tiene un valor m´aximo controlado, las componentes del vector transformado tienden a cero cuando N → ∞. De hecho es esperable que este decrecimiento sea uniforme en todas las componentes, es decir, 1 Rj ≈ √ N 142

´ III LECCION

Cap´ıtulo 7. F´ormulas de cuadratura. FFT

Señal continua con un muestreo de 64 puntos 1

1

0.5

0.5

r do rra Bo 0

0

-0.5

-0.5

-1 0

0.2

0.4

0.6

0.8

-1 0

1

Coef. Fourier (en valor absoluto)

0.4

0.6

0.8

1

FT de la señal discreta (valor abs.)

0.4

0.4

0.3

0.3

0.2

0.2

0.1

0.1

0 -40

0.2

-20

0

20

0

40

0

10

20

30

40

50

60

Figura 7.7: Coeficientes de Fourier y transformada discreta de Fourier

Ahora, si consideramos la influencia de este ruido sobre una se˜ nal y, tenemos la se˜ nal e = y + r. Se trata ahora de eliminar ese ruido observando la transformada perturbada y e Y. La estrategia que planteamos es la siguiente. En el caso de que Yej sea grande, podemos aceptar este coeficiente dado que el error relativo es peque˜ no. Por contra, si Yej es peque˜ no, el error relativo que hemos introducido es tal que la informaci´on ha quedado irremediablemente contaminada y por tanto debemos desecharla. Lo anterior sugiere una forma de depurar la se˜ nala, partiendo de un nuevo vector Z ( 0 si |Yek | es peque˜ no, (7.11) Zk = Yek en otro caso. Con la informaci´on que nos queda, reconstruimos la se˜ nal discreta original y mediante −1 F Z. As´ı tenemos el siguiente diagrama y

+ ruido

−→

e y

F

−→

e Y

(7.11) −→ Z

F −1

−→

z.

Al final de proceso, z es (deber´ıa ser) mejor aproximaci´on de y que la se˜ nal perturbada e. y En la Figuras 7.9 se muestran los resultados obtenidos con n = 64 y n = 256. Se puede observar como la se˜ nal es filtrada eliminando gran parte del ruido introducido. 143

´ III LECCION

7.2 Transformada r´apida de Fourier

0.08

0.015

0.06

r do rra Bo

0.01

0.04

0.005

0.02

0

10

20

30

0

40

0.08

8

0.06

6

0.04

4

0.02

2

0

50

100

10

x 10

0

150

20

30

40

-3

50

100

150

Figura 7.8: Ruido en un conjunto de puntos (40 arriba, 160 abajo) y su transformada discreta

7.2.4.

Transformada r´ apida de Fourier

La importancia del an´alisis de Fourier, y por ende de la transformada discreta de Fourier, fue cobrando fuerza a lo largo del siglo XX y muchos aspectos siguen demandando este tipo de t´ecnicas en el siglo actual. Pronto surgieron problemas que requer´ıan calcular la transformada de Fourier de millones de elementos, lo que colocaba el problema m´as all´a de la potencia de los ordenadores umero de de la ´epoca y los de un futuro previsible18 . En cualquier caso duplicar N , el n´ elementos de y, requerir´ıa multiplicar por cuatro la potencia del ordenador. Siguiendo el progreso de la inform´atica, esto significar´ıa una espera de 36 meses19 . 18

Hemos mostrado algunas aplicaciones simples de la transformada de Fourier que son esencialmente unidimensionales (una se˜ nal peri´ odica). Existen aplicaciones que exigen trabajar ya con se˜ nales bidimensionales. En ese caso, duplicar la precisi´ on con la que se trabaja implica multiplicar por 4 la dimensi´on del problema y por 16 la complejidad computacional del algoritmo que hemos visto. Problemas en m´as dimensiones y con n´ umeros muy elevados de variables no son extra˜ nos. 19 La ley de Moore formulada por Gordon Moore cofundador de Intel en 1965 es un ejemplo de una ley emp´ırica que se viene satisfaciendo con asombrosa regularidad en los u ´ltimos cuarenta a˜ nos. Esta ley establece que la potencia de c´ alculo y la capacidad de almacenamiento se multiplica por 2 cada 18 meses. De forma paralela han surgido otras versiones de la ley de Moore que establecen comportamientos de crecimiento exponencial en el mundo de la inform´atica.

144

´ III LECCION

Cap´ıtulo 7. F´ormulas de cuadratura. FFT

64 puntos

Señal con ruido

FT (en valor absoluto)

1 0.4 0.35 0.5

0.3

r do rra Bo 0.25

0

0.2

0.15

-0.5

0.1

0.05

-1

0

0.2

0.4

0.6

0.8

0

1

0

10

20

Truncacion de la FT

30

40

50

60

Señal filtrada

1

0.4

0.35

0.5

0.3

0.25

0

0.2

0.15

-0.5

0.1

0.05 0

0

10

20

30

40

50

-1

60

0

256 puntos

Señal con ruido

0.2

0.4

0.6

0.8

1

FT (en valor absoluto)

1

0.4

0.35

0.5

0.3

0.25

0

0.2

0.15

-0.5

0.1

0.05

-1

0

0.2

0.4

0.6

0.8

0

1

0

50

Truncacion de la FT

100

150

200

250

Señal filtrada

1

0.4

0.35

0.5

0.3

0.25

0

0.2

0.15

-0.5

0.1

0.05 0

0

50

100

150

200

-1

250

0

0.2

Figura 7.9: Filtrado del ruido 145

0.4

0.6

0.8

1

´ III LECCION

7.2 Transformada r´apida de Fourier

En 1965, Jim Cooley, investigador ligado a IBM y John Tukey, de la Universidad de Princeton mostraron una forma sencilla de programar la transformada de Fourier discreta que reduc´ıa dr´asticamente el n´ umero de operaciones. La idea de partida del algoritmo es considerar el caso N = 2m. Entonces denotando ω1 := ω 2

r do rra Bo se tiene que

ω 2jk = (ω 2 )kj = ω1jk .

De esta forma, si 0 ≤ k ≤ M − 1 = N/2 − 1 Yk

N −1 M −1 M −1 1 X 1 X 1 X jk 2jk yj ω = y2j ω + y2j+1 ω (2j+1)k N j=0 N j=0 N j=0 {z } | {z } |

=

Pares

N = 2M

↓ =

=:

(0)

Impares

M −1 M −1 i 1 X 1h 1 X y2j ω1jk + ω k y2j+1 ω1jk 2 M j=0 M j=0 i h 1 (0) (1) Yk + ω k Yk . 2

(7.12)

(1)

Notemos que Yk e Yk son el resultado de aplicar la transformada de Fourier discreta a los vectores (y0 , y2 , . . . , y2M −2 )> y a (y1 , y3 , . . . , y2M −1 )> respectivamente, que son vectores de longitud M = N/2. Si M ≤ k ≤ N − 1 la relaci´on cambia levemente. Para ello, escribamos k = M + κ, donde ahora 0 ≤ κ ≤ M − 1. Entonces Yk

N −1 M −1 M −1 1 X 1 X 1 X jk 2jk yj ω = y2j ω + y2j+1 ω (2j+1)k = N j=0 N j=0 N j=0

=

M −1 M −1 i 1h 1 X 1 X y2j ω1jM ω1jκ + ω M ω κ y2j+1 ω1jκ . 2 M j=0 M j=0

Dado que

ω M = exp(−πi) = −1,

ω1M = 1;

se deduce que

 1  (0) (7.13) Yκ − ω κ Yκ(1) . 2 v Denotando por w el vector resultado de enlazar los vectores v y w, las identidades (7.12) y (7.13) se puede escribir en notaci´on vectorial   1 Y(0) + ω. ∗ Y(1) Y= (7.14) 2 Y(0) − ω. ∗ Y(1) Yk =

donde Y(0) e Y(1) son las transformadas de Fourier de los vectores (y0 , y2 , . . . , y2M −2 )> y (y1 , y3 , . . . , y2M −1 )> , ω = (ω 0 , ω 1 , . . . , ω M −1 )> , 146

ω := exp(− 2πi ), N

(7.15)

´ III LECCION

Cap´ıtulo 7. F´ormulas de cuadratura. FFT

y “.*” denota el producto elemento a elemento entre las componentes de los vectores. En cuando al n´ umero de operaciones, si f (N ) es el n´ umero de multiplicaciones, se comprueba que el total de productos es el de dos transformadas de longitud N/2 m´as N productos realizados al combinar dichas transformadas. En resumen,

r do rra Bo

f (N ) = 2f (N/2) + N.

Nada nos impide aplicar de forma reiterada el algoritmo anterior para calcular Y(0) e Y(1) si M es divisible por 2 (o lo que es lo mismo, que N sea divisible por 4). De forma natural, se puede programar el m´etodo de forma recursiva. El caso ´optimo del algoritmo en la versi´on anterior se da cuando N = 2p . El algoritmo queda de la siguiente forma FFT

N =length(y) if N==1 Y=y else Y(0) := FFT(y(0 : 2 : N − 2)) % Parte ‘‘par’’ Y(1) := FFT(y(1 : 2 : N − 1)) % Parte ‘‘impar’’ ω = exp(−2πi/N ) ω := [ω 0 , ω 1 , . . . , ω N/2−1 ]> Y(0 : N/2 − 1) = (Y(0) + ω. ∗ Y(1) )/2 Y(N/2 : N − 1) = (Y(0) − ω. ∗ Y(1) )/2 end

En tal caso, se puede comprobar que el n´ umero de productos es f (N ) = 2p (p + 1) = N (log2 (N ) + 1)

que debe compararse con el N 2 esperable de la implementaci´on directa. De ah´ı viene el nombre de Transformada R´ apida de Fourier.

Ejercicio 7.24 Implementa la transformada r´apida de Fourier.

Ayuda. No utilices fft como nombre de esta funci´on, dado que ´este es el comando de Matlab para el c´alculo de la transformada r´apida de Fourier. Entrando ya en programa, en primer lugar podemos plantearnos c´omo se va a devolver el resultado, si como un vector fila o como un vector columna. Para ello, la primera instrucci´on de nuestra subrutina podr´ıa ser y=y(:); Y=y; si se quiere trabajar s´olo con columnas, o 147

´ III LECCION

7.2 Transformada r´apida de Fourier y=y(:).’; Y=y;

si se desea implementar para filas. F´ıjate que ya hemos introducido el vector que va a guardar la transformada de Fourier y que sus dimensiones coinciden con las del vector y. Llegado a este punto, hay que tener cuidado al programar el producto

r do rra Bo

ω. ∗ Y(1)

para que los vectores implicados, ω e Y(1) tengan igual dimensi´on. Si el vector tiene un n´ umero par de elementos, la transformada se calcula a partir de la transformada de los vectores y(1 : 2 : n) y(2 : 2 : n)

−→ −→

(y0 , y2 , . . . , yn−2 )> , (y1 , y3 , . . . , yn−1 )> ,

(Y(0) ) (Y(1) )

de acuerdo con el algoritmo (v´ease tambi´en (7.14) y (7.15)). Cuando el n´ umero de entradas de y no sea una potencia de 2 se puede utilizar el primer algoritmo que dimos (ejercicio 7.22). De esta manera tendr´ıamos la siguiente estructura

y=y(:); n=length(y); if mod(n,2)==0 ...... % expresion RECURSIVA en terminos de dos transformadas ...... else % no es divisible por 2 ...... % Algoritmo del ejercicio 7.22 end

En las l´ıneas anteriores, mod(m,n) devuelve el resto de la divisi´on de m entre n y sirve para comprobar si el n´ umero de entradas es par o impar.

Ejercicio 7.25 Implementa una funci´on recursiva que devuelva el n´umero de operaciones para el c´alculo de la FFT. Util´ızala para obtener una tabla con el n´umero de operaciones para algunos valores altos de N . Compara con el n´umero de operaciones requerido en la versi´on inicial del algoritmo dada antes. ´ Soluci´ on. Esta es una forma simple de implementar la funci´on

01 02 03 04 05 06 07 08 09 10 11 12 13

% OPERACIONESFFT(N) % % M=OPERACIONESFFT(N) % % M es el numero de operaciones de la FFT function M=operacionesFFT(N)

if mod(N,2)==1 M=N^2; else M=operacionesFFT(N/2)*2+N; end

148

´ III LECCION

Cap´ıtulo 7. F´ormulas de cuadratura. FFT

´ Hemos testado la funci´on con 219 y 219 − 1 que es primo. Este es el resultado



r do rra Bo

>> format rat >> operacionesfft(2^19) %(2^19 approx 500.000) ans=

10485760

>> operacionesfft(2^19-1) ans =

274876858369

Observa que el n´ umero de operaciones efectuadas se reduce en un factor de 26000 si aumentamos en uno el n´ umero de elementos. Ejercicio 7.26 Implementa la Inversa de la Transformada Discreta de Fourier con nombre InvTrRaFourier.

Ejercicio 7.27 En este ejercicio observaremos la dependencia de la FFT implementada en Matlab respecto del n´umero de entradas del vector. Para ello, utilizaremos de nuevo los valores 219 − 1 y 219 propuesto anteriormente. Define dos vectores y1 y y2 con 219 − 1 y 219 componentes respectivamente, por ejemplo, mediante la orden rand. Aplica fft(y1) y fft(y2) y comprueba el tiempo que tarda en cada caso. ¿Sabr´ıas explicar por qu´e se reduce el tiempo de c´alculo?. Nota final

Las implementaciones comerciales de la FFT son ciertamente m´as complicadas que lo que hemos visto. En realidad, los m´etodos recursivos son menos eficientes que las implementaciones directas, que no hacen uso de la recursividad. En lugar de ello se opta por una programaci´on directa, m´as refinada. No s´olo se descompone la transformada en dos de longitud mitad de la original, como se ha mostrado en este algoritmo, sino que adem´as se intenta dividir por los primeros n´ umeros primos 2, 3, 5, 7,... reduci´endola a dos, tres, cinco o siete transformadas y as´ı sucesivamente. Incluso el caso de n´ umeros primos se realiza de forma m´as ´optima que el algoritmo (ingenuo) del ejercicio 7.22. Los comandos en Matlab que devuelven la transformada de Fourier y su inversa son fft e ifft. Puede consultarse la ayuda para ver algunos detalles sobre su funcionamiento e implementaci´on. Existen otras transformadas ligadas a ´esta. Por ejemplo, la transformada del coseno y la del seno, tambi´en implementadas en Matlab (dct, idct, dst y idst). . 149

´ III LECCION

7.2 Transformada r´apida de Fourier La FFT y el producto de n´ umeros enteros Dados dos vectores u = (u0 , u1 , . . . , ur )> ,

v = (v0 , v1 , . . . , vs )>

r do rra Bo

se define el vector convoluci´on u ∗ v al vector de r + s + 1 componentes cuya entrada k viene dada por m´ın{k,r}

X

(u ∗ v)k :=

X

u` v j =

`+j=k

u` vk−` ,

(7.16)

(k = 0, . . . , r + s).

`=m´ ax{0,k−s}

Es f´acil comprobar que la convoluci´on, tambi´en llamado producto de convoluci´on, es conmutativo. Esta operaci´on es simplemente el producto de polinomios. En efecto, si consideramos los polinomios u0 + u 1 x + . . . + u r x r ,

v0 + v1 x + . . . + vs xs

entonces el coeficiente en xk del polinomios producto viene dado precisamente por (7.16). Una propiedad interesante de la transformada de Fourier discreta es que convierte la convoluci´on de dos vectores en producto de transformadas. Tomemos N = r + s. Si u y v se insertan en Rn+1 rellenando con ceros u = (u0 , u1 , . . . , ur ,

0, . . . , 0 | {z }

)> , v = (v0 , v1 , . . . , vs ,

N − r = s ceros

0, . . . , 0 | {z }

)

N − s = r ceros

tenemos que

F (u ∗ v) = N (F (u). ∗ F (v)),

donde la operaci´on anterior es el producto elemento a elemento entre los vectores. As´ı, una forma r´apida de calcular la convoluci´on de los dos vectores es seguir el siguiente algoritmo Calcular U = F (u), V = F (v) Multiplicar W = N U. ∗ V Devolver F −1 (W)

Si N = r + s es una potencia de 2 entonces el n´ umero de operaciones es del orden de O(n log2 (N )), comparado con 2N 2 que tiene la implementaci´on m´as directa. Una de las aplicaciones m´as simples del c´alculo de productos de convoluci´on est´a en el producto de n´ umeros enteros. Por ejemplo,  6031 → 1 + 3 · 10 + 0 · 102 + 6 · 103 ⇒ 1234 → 4 + 3 · 10 + 2 · 102 + 1 · 103



6031 × 1234 = 4 + 15 · 101 + 11 · 102 + 31 · 103 + 21 · 104 + 12 · 105 + 6 · 106 = 7442254.

Es decir, se trata simplemente del producto de polinomios con “10” jugando el papel de “x”, o equivalentemente, la convoluci´on entre dos vectores:  6031 → (1, 3, 0, 6, 0, 0, 0, 0) =: u ⇒ u ∗ v = (4, 15, 11, 31, 21, 12, 6)> 1234 → (4, 3, 2, 1, 0, 0, 0, 0) =: v

Por tanto, la FFT nos ofrece una forma muy r´apida de multiplicar dos n´ umeros enteros. 150

´ III LECCION

Cap´ıtulo 7. F´ormulas de cuadratura. FFT

Ejercicio 7.28 Implementa una funci´on que calcule el producto de dos n´umeros enteros con la transformada de Fourier de acuerdo al siguiente prototipo

r do rra Bo

% MULTIPLICACION % % % P=MULTIPLICACION(A,B) % % % % %

Devuelve el producto de A por B

A,B deben ser arrays de caracteres P es un array de caracteres con el producto A*B

Ayuda. Para que el m´etodo sea realmente eficiente necesitamos que los vectores sobre los que se va a aplicar la transformada de Fourier tengan longitud una potencia de 2. Para ello podemos insertar m´as ceros de los inicialmente previstos de forma que N sea una potencia20 de 2. Para disponer de una precisi´on en principio ilimitada, introduciremos los n´ umeros que deseamos multiplicar en una cadena de caracteres y haremos la salida en el mismo formato. Para su implementaci´on necesitaremos manejarnos con la conversi´on entre los diversos formatos de datos. Una cadena o string es simplemente un vector de caracteres y as´ı lo maneja Matlab: >> p=’esto es una prueba’ ans=

esto es una prueba

>> p(3) ans=

t

>> p(6:9) ans = es u

Har´a falta transformar un vector de caracteres a un vector de n´ umeros y viceversa. Para ello se puede utilizar los comandos str2num, num2str(STRing-to-NUMeric y NUMericto-STRing). Una vez que tengamos el vector de n´ umeros hay que darle la vuelta al vector, de forma que ’1234’ [4 3 2 1]. 20

¿Qu´e hace log2(ceil(r+s))?

151

´ III LECCION

7.2 Transformada r´apida de Fourier

Por u ´ltimo una vez multiplicados hay un paso de acarreo, es decir, un resultado de forma que [4 15 11 31 21 12 6]

4 + 15 · 101 + 11 · 102 + 31 · 103 + 21 · 104 + 12 · 105 + 6 · 106

debe transformarse en su representaci´on decimal

r do rra Bo 4 + 5 · 101 + 2 · 102 + 2 · 103 + 4 · 104 + 4 · 105 + 7 · 106 = 744224.

Nota. ¿Para qu´e preocuparse en multiplicar n´ umeros enteros? Es decir, no parece haber una necesidad acuciente de dise˜ nar algorimos para multiplicar n´ umeros de centenares o miles de cifras. Una aplicaci´on sorprendente proviene del mundo de cifrado de mensajes. El sistema de cifrado m´as popular actualmente es el RSA, propuesto por los matem´aticos21 Ron Rivest, Adin Shamir y Len Adleman en 1977, est´a basado en el conocido Teorema Peque˜ no de Fermat22 . Este teorema, muy simple, tiene que ver con los restos de la divisi´on por n´ umeros primos. El mensaje que se desea enviar se convierte en un n´ umero entero, m´as o menos largo. El cifrado y descifrado del mensaje se basa en calcular restos de divisiones por el producto de dos n´ umeros primos muy grandes. La seguridad del sistema depende directamente del tama˜ no de estos primos: mayor tama˜ no es mayor seguridad. Ello hace que se requiera calcular productos y divisiones de n´ umeros enteros enormes de  forma r´apida y eficiente23 .

Nota. La convoluci´on est´a implementada en Matlab mediante el comando conv. La forma de calcular es esencialmente la expuesta en esta secci´on. 

21

El nombre del algoritmo son las iniciales de sus apellidos. ´ Nada que ver con el Ultimo Teorema de Fermat, cuya demostraci´on tuvo que esperar cuatro siglos. 23 Para una informaci´ on m´ as detallada, m´ırese por ejemplo http://en.wikipedia.org/wiki/Rsa. 22

152

r do rra Bo Lecci´on IV

C´alculo simb´olico, arrays y celdas en Matlab. Valores y vectores propios. Google.

153

r do rra Bo

r do rra Bo

Introducci´ on

La physique ne nous donne pas seulement l’occasion de r´esoudre des probl`emes... elle nous fait pressentir la solution Henri Poincar´e

En la primera parte de esta lecci´on trataremos diversos aspectos instrumentales de Matlab, como el manejo de polinomios, arrays multidimensionales (tensores) y vectores de celdas. Daremos adem´as algunos esbozos sobre la manipulaci´on de expresiones simb´olicas. Aunque en este campo Matlab no es comparable a otros manipuladores simb´olicos como Maple o Mathematica, puede resultar en muchos casos suficiente. En la segunda parte trataremos el c´alculo de valores y vectores propios de Matlab. Volvemos por tanto a incidir en el manejo de vectores y matrices, y en ese sentido es un recordatorio de lo que vimos en las Lecciones 1 y 2. Con el fin de aliviar el peso te´orico de la parte matem´atica, terminaremos con un cap´ıtulo fundamentalmente divulgativo sobre Google y su algoritmo de evaluaci´on de p´aginas web Pageranktm .

155

r do rra Bo

r do rra Bo

Cap´ıtulo 8

Matlab: C´ alculo simb´ olico y estructuras de datos. 8.1.

Polinomios y c´ alculo simb´ olico

Los polinomios constituyen las funciones m´as simples en Matem´aticas y computacionalmente son importantes habida cuenta que contienen en su estructura las operaciones b´asicas en un ordenador. En esta secci´on veremos como maneja Matlab un polinomio y nos servir´a de preparaci´on para la secci´on siguiente donde veremos someramente la toolbox de c´alculo simb´olico.

8.1.1.

Polinomios

Matlab maneja un polinomio identific´andolo simplemente con un vector de n´ umeros > (en principio) reales. Concretamente, el vector fila (an , . . . , a0 ) corresponde al polinomio an xn + an−1 xn−1 + . . . + a0 . Si alg´ un coeficiente es nulo, debe incluirse. Por ejemplo, el vector (1, 0, 2)> representa el polinomio x2 + 2. Sumar y restar dos polinomios se reduce as´ı a sumar y restar dos vectores, salvando el problema de que ambos deben tener el mismo grado: >> p=[2 0 1]; % 2*x^2+1 >> q=[-1 1 -1 0 1]; % -x^4+x^3-x^2+1 >> p+q % ERROR!! ??? Error using ==> plus Matrix dimensions must agree. >> p=[0 0 2 0 1]; >> p+q

% dos coeficientes mas % ahora OK!

ans=

-1

1

1

0

2

El producto y divisi´on de polinomios est´an implementados respectivamente en los comandos conv y deconv 157

´ IV LECCION

8.1 Polinomios y c´alculo simb´olico >> p=[2 0 1]; q=[-1 1 -1 0 1]; >> conv(p,q) ans = 2

-3

1

1

0

1

r do rra Bo

-2

>> deconv(q,p) ans=

-0.5000

0.5000

-0.2500

Ejercicio 8.1 Implementa una funci´on que calcule la suma de dos polinomios, su producto, cociente y resto seg´un el siguiente prototipo 01 02 03 04

OPERACIONESPOL(P1,P2)

[S,R,C,P]= OPERACIONESPOL(P1,P2)

S, R, C y P son la suma, resta cociente y producto de P1 y P2

(Ayuda: P1 y P2 deben ser de la misma longitud. ¿Qu´e hace la instrucci´on p1=[zeros(1,length(p2)-length(p1)) p2]

cuando length(p2)>length(p1)? Comprueba que tambi´en es v´alida cuando length(p2)> p=[1 0 0 1 0 3]; %definimos el polinomio x^5+x^2+3 >> polyval(p,2) %evaluamos en x=2 ans = 39

>> polyval(p,[1 2 3]) %vectorizado ans = 5

39

255

Ra´ıces de polinomios

Las ra´ıces de un polinomio p son las soluciones de la ecuaci´on p(x) = 0. El Teorema 1 ´ Fundamental del Algebra afirma que un polinomio de grado n tiene exactamente n ra´ıces en C (alguna puede estar repetida). 1

Demostrado por primera vez por Carl Friedrich Gauss en 1799 (a los 22 a˜ nos) en su tesis doctoral. Gauss ha salido repetidamente en estas lecciones y en campos muy distintos, desde las Matem´aticas m´as aplicadas a las m´ as puras. Quiz´ as ahora se comprenda mejor por qu´e recibi´o el sobrenombre de“pr´ıncipe de las Matem´ aticas”.

158

´ IV LECCION

Cap´ıtulo 8. Matlab: C´alculo simb´olico y estructuras de datos.

En Matlab podemos utilizar roots para calcular de forma aproximada las ra´ıces de un polinomio: >> pol=[2 -3 -17 30]; % 2*x^2-3*x^2-17*x+30 >> roots(pol)

r do rra Bo ans =

-3.0000 2.5000 2.0000

>> pol2=[1 -2 2 -1]; >> roots(pol2).’ % un par complejas!! ans =

1.0000

0.5000 + 0.8660i

0.5000 - 0.8660i

Rec´ıprocamente, dado un vector que contenga las ra´ıces, podemos crear un polinomio m´onico (el coeficiente que acompa˜ na a la mayor potencia de x es 1) cuyas ra´ıces sean las dadas: >> poly([-3 5/2 2]) ans =

1

-3/2

-17/2

15

El comando poly puede emplearse tambi´en para construir el polinomio caracter´ıstico de una matriz cuadrada A, es decir, el polinomio det(A − xI)

donde I es la matriz identidad de orden n. Por ejemplo, >> A=[3 -2 2;-1 2 2;-1 1 3]; >> p=poly(A) %pol caract. (monico) p =

1

-8

19

>> roots(p).’ ans = 4

3

1 159

-12

´ IV LECCION

8.1 Polinomios y c´alculo simb´olico

En la segunda parte de esta lecci´on nos centraremos en los m´etodos num´ericos para el c´alculo de las ra´ıces de estos polinomios2 .

r do rra Bo

Nota. Un problema cl´asico3 es la determinaci´on de las ra´ıces de un polinomio. La ecuaci´on de segundo grado aparece m´as o menos resuelta en las Matem´aticas antiguas: babil´onicas, griegas, hind´ ues y ´arabes. Es un hecho muy resaltable que no exist´ıa una f´ormula para la soluci´on como la como la que conocemos hoy en d´ıa, sino que los autores describ´ıan diversas ecuaciones, habitualmente con ejemplos concretos, para luego explicar c´omo se proced´ıa a resolverlas4 a menudo con razonamientos geom´etricos que exclu´ıan cualquier resultado negativo. Fue en las matem´aticas hind´ ues donde las ra´ıces negativas fueron consideradas como v´alidas. Las matem´aticas italianas primero y europeas despu´es retoman a partir del siglo XV las ecuaciones polin´omicas. Nicolo Fontana Tartaglia, Girolamo Cardano, Fran¸cois Vi`ete, Ren´e Descartes, Gottfried Wilhelm von Leibniz, Joseph-Louis Lagrange y Leonhard Euler entre otros matem´aticos de menor renombre, estudiaron la resoluci´on por radicales de ecuaciones polin´omicas de tercer y cuarto grado con un resultado final satisfactorio: se consigui´o dar con f´ormulas que proporcionaban las ra´ıces de un polinomio de grado 4. Sin embargo fueron incapaces de encontrar una f´ormula para la ecuaci´on general de quinto grado. La cuesti´on qued´o zanjada de forma sorprendente: Niels Henrik Abel prob´o en 1824 (a los 22 a˜ nos) que no exist´ıa un f´ormula que diera las ra´ıces de cualquier polinomio de ´ltima medida, grado 5 mediante la aplicaci´on de radicales5 tomando ra´ıces en´esimas. En u se hab´ıa llegado a la conclusi´on de que era imposible la resoluci´on exacta de ecuaciones polin´omicas de grado mayor o igual que cinco. El estudio de cu´ando una ecuaci´on se pod´ıa resolver mediante radicales fue iniciado por Evariste Galois6 . Otro asunto muy diferente es la resoluci´on num´erica del problema. Se dispone de una familia de m´etodos para la resoluci´on de problemas no lineales generales (es decir, para ecuaciones de la forma f (x) = 0 donde f es una funci´on cualquiera, no necesariamente polin´omica) como los m´etodos de Newton-Raphson, secante, regula–falsi, etc. Sin embargo, dadas las particulares propiedades de los polinomios, hay m´etodos especialmente dise˜ nados para tal fin. Algunos m´etodos cl´asicos son los de Bairstow y el de Bernoulli. En los u ´ltimos a˜ nos el c´alculo de las ra´ıces de un polinomio ha quedado reducido al c´alculo 2

Las ra´ıces son los valores propios de la matriz A. La informaci´ on de estas l´ıneas se ha extra´ıdo de la web “MacTutor History of Mathematics Archive” de la Universidad de St. Andrews (Escocia). La direcci´on electr´onica es http://turnbull.mcs.stand.ac.uk/history/ 4 al-Khwarizm clasific´ o y explic´ o c´ omo resolver ecuaciones de segundo grado en 6 tomos. El desarrollo ´ del Algebra y la manipulaci´ on simb´ olica de expresiones ha conseguido que este problema pueda ser planteado en nuestros d´ıas a un alumno de primaria. 5 Paolo Ruffini hab´ıa dado una demostraci´on no del todo correcta en 1799. 6 Galois y Abel comparten algunas caracter´ısticas en com´ un, ambos murieron jovenes (Abel a los 29 a˜ nos y Galois a los 21) con buena parte de su trabajo ignorado por la comunidad matem´atica. La muerte de Galois es todav´ıa m´ as sorprendente. Franc´es y republicano convencido, lleg´o a estar en prisi´on por ello, muri´o en un duelo en 1832 en los a˜ nos convulsos posteriores a la revoluci´on francesa, aunque no est´a claro si ´este fue por motivos pol´ıticos o de otra ´ındole. En la noche anterior al duelo escribir´ıa en el margen de unas notas sobre las que trabaja: “Falta algo para completar la demostraci´ on. No tengo tiempo.”. Esta frase ha cimentado la, probablemente exagerada, leyenda de que paso la noche escribiendo Matem´aticas. Su trabajo fue rescatado del olvido por Joseph Liouville 11 a˜ nos despu´es. 3

160

´ IV LECCION

Cap´ıtulo 8. Matlab: C´alculo simb´olico y estructuras de datos.

de los valores propios de una matriz, simplemente construyendo la matriz compa˜ nera7 −an−1 −an−2  1 0   0 1   ..  . 0 0  xn + an−1 xn−1 + . . . a0

r do rra Bo

 · · · −a1 −a0 ··· 0 0   ..  . 0 0  ..  .. .. . . .  ··· 1 0

Al c´alculo de los valores propios de una matriz volveremos en la segunda parte de esta lecci´on. 

8.2.

Procesador simb´ olico

Retomando el hilo de la secci´on anterior, otra forma de operar con polinomios es de manera simb´olica. Para ello podemos proceder del siguiente modo: >> syms x %define x como variable simbolica >> (x^4+x^2-1)+(2*x^3+4*x^2+3) %suma de polinomios ans =

x^4+5*x^2+2+2*x^3

>> expand((x^4+x^2-1)*(2*x^3+4*x^2+3))

%expande el producto

ans =

2*x^7+4*x^6+2*x^5+7*x^4-2*x^3-x^2-3

Observa con atenci´on la primera instrucci´on. Con syms, declaramos x con una variable simb´olica y por tanto susceptible de entrar en expresiones y manipulaciones algebraicas. Las ´ordenes anteriores pueden aplicarse sobre funciones cualesquiera, no necesariamente polin´omicas: >> syms x y >> expand(cos(x+y)) ans=

cos(x)*cos(y)-sin(x)*sin(y)

Podemos llevar a cabo operaciones de c´alculo b´asico tales como la integraci´on o la derivaci´on: 7

De hecho, as´ı procede roots.

161

´ IV LECCION

8.2 Procesador simb´olico >> diff(x*cos(x^2))

%derivada

ans = cos(x^2)-2*x^2*sin(x^2)

r do rra Bo >> diff(x^4+x^2-1,3)

%tercera derivada

ans =

-24*x^2*cos(x^2)-6*sin(x^2)+8*x^4*sin(x^2)

>> int(exp(x)*cos(4*x),x)

%integral indefinida

ans =

1/17*exp(x)*cos(4*x)+4/17*exp(x)*sin(4*x)

>> int(exp(x)*cos(4*x),x,0,pi)

%integral definida

ans =

1/17*exp(pi)-1/17

De forma similar se pueden calcular l´ımites (limit), sumar series (symsum), >> sym k; >> symsum(1/k^2,k,1,inf) ans=

1/6*pi^2

hacer desarrollos de Taylor (taylor) o transformadas integrales como las de Fourier o Laplace (fourier, ifourier, laplace e ilaplace) Observa como los resultados son s´ımbolos y no n´ umeros. En cualquier caso, el comando vpa procede a evaluar con la precisi´on solicitada (si es posible) >> vpa( 1/17*exp(pi)-1/17)

% 32 cifras por defecto

ans=

1.3023936842811332237346277906909

>> vpa( 1/17*exp(pi)-1/17,64)

% ahora con 64 cifras

ans= 1.3023936842811332237346277906908653676509857177734375000 162

´ IV LECCION

Cap´ıtulo 8. Matlab: C´alculo simb´olico y estructuras de datos.

Nota. La derivaci´on e integraci´on de un polinomio se puede hacer tambi´en con polyder y polyint que trabaja directamente sobre el vector que almacena el polinomio, es decir, no es simb´olico: >> polyder([1 4 2]) % derivada de x^2+4*x-2

r do rra Bo ans=

2

4



Ejercicio 8.2 Los siguientes comandos inciden en la simplificaci´on y manipulaci´on de expresiones simplify

factor

expand

collect

simple

Consulta la ayuda de Matlab y apl´ıcalos sobre diferentes expresiones algebraicas susceptibles de ser simplificadas.

Para la resoluci´on de ecuaciones y sistemas de ecuaciones mediante m´etodos simb´olicos, con las limitaciones que esto implica, podemos utilizar el comando solve: >> solve(’x*log(x^2+4*x-4)=0’) ans =

0 1 -5

Cuando el t´ermino independiente es cero puede omitirse: >> solve(’x*log(x^2+4*x-4)’)

De forma an´aloga, dsolve busca las soluciones de ecuaciones y sistemas diferenciales: >> dsolve(’D3y-D2y-2*Dy-cos(s)’,’s’) % y’’’-y’’-2y’-cos(s)=0 ans =

-3/10*sin(s)+1/10*cos(s)+C1+C2*exp(2*s)+C3*exp(-s)

>> dsolve(’D3y-D2y-2*Dy-cos(s)’,’y(0)=1’,’Dy(0)=2’, ’D2y(0)=3’,’s’) ans =

-3/10*sin(s)+1/10*cos(s)+1/2+9/10*exp(2*s)-1/2*exp(-s)

Ejercicio 8.3 Utiliza solve para hallar las cuatro ra´ıces de la ecuaci´on de cuarto grado x4 + ax3 + bx2 + cx + d. 163

´ IV LECCION

8.3 Tensores

r do rra Bo

Nota. Matlab es un programa m´as enfocado al c´alculo num´erico que al simb´olico. Ciertamente los resultados son presentados de una forma que est´eticamente no es comparable a Mathematica o Maple. Sin embargo se puede acceder a cualquier instrucci´on de Maple luego a priori todo lo que se puede hacer con este procesador se puede hacer con Matlab. Para llamar a un comando de Maple se utiliza el comando maple, mientras que a la ayuda correspondiente se accede con mhelp. 

8.3.

Tensores

Ya hemos hablado en m´ ultiples ocasiones de la gran potencia que posee Matlab para 8 realizar c´alculos matriciales y su habilidad en el manejo de grandes cantidades de memoria. Estas habilidades se extienden a la manipulaci´on de arrays multidimensionales, que matem´aticamente se puede identificar con tensores. Un tensor es simplemente una matriz multidimensional, esto es, si una matriz se puede interpretar como una tabla de n´ umeros, un tensor (o array) tridimensional es simplemente un conjunto de n´ umeros desplegados en 3D en forma de paralelogramo. As´ı >> a=zeros(1,3,2) a(:,:,1) = 0

0

0

0

0

a(:,:,2) = 0

define un array de una fila, tres columnas y dos alturas. Abandonaremos en lo que sigue este s´ımil geom´etrico pues aporta poco. Se puede declarar un tensor simplemente dando sus valores >> a2(:,:,1)=[1 2 3;4 5 6] a2 =

1 4

2 5

3 6

>> a2(:,:,2)=[7 8 9;10 11 12] a2(:,:,1) = 1 4

8

2 5

3 6

Recuerda Matlab = Matrix laboratory

164

´ IV LECCION

Cap´ıtulo 8. Matlab: C´alculo simb´olico y estructuras de datos.

a2(:,:,2) = 8 11

9 12

3

2

r do rra Bo

7 10

>> size(a) ans =

2

>> length(a)

%maximo de las dimensiones

ans =

3

Observa la diferencia

>> a1=a(1,:,:) a1(:,:,1) = 1

2

3

a1(:,:,2) = 7

8

9

>> a2=a(:,1,:) a2(:,:,1) = 1 4

a2(:,:,2) = 7 10

>> a3=a(:,:,1) a3 =

165

´ IV LECCION

8.3 Tensores 1 4

2 5

3 6

r do rra Bo

Por tanto, de las variables que acabamos de definir u ´nicamente a3 es una matriz propiamente dicha. La forma de operar con tensores es b´asicamente la misma que con vectores y matrices. Por ejemplo: >> b=a+ones(2,3,2) b(:,:,1) = 2 5

3 6

4 7

9 12

10 13

b(:,:,2) = 8 11

>> b(:,2:3,2)=[-1 -2;-3 -4] b(:,:,1) = 2 3

3 3

4 3

-1 -3

-2 -4

b(:,:,2) = 8 3

>> b(:)’ % como se guarda en memoria... ans = 2

3

3

3

4

3

8

3

-1

-3

-2

-4

Ejemplo. Mediante las siguientes ordenes calculamos las cinco primeras potencias de la matriz a y las almacenamos en una variable tridimensional b: a=[1 2;3 4]; b(:,:,1)=a; for i=2:5 b(:,:,i)=b(:,:,i-1)*a; end

%b(:,:,i) guarda a^i

 166

´ IV LECCION

Cap´ıtulo 8. Matlab: C´alculo simb´olico y estructuras de datos.

r do rra Bo

Las funciones que operan sobre escalares, tales como sin, cos, etc., funcionan con tensores exactamente del mismo modo que con vectores o matrices, realizando las operaciones elemento a elemento. Si se aplica una funci´on de las que operan sobre los elementos de un tensor como por ejemplo b´ usqueda de m´aximos o m´ınimos (max, min) o la suma y producto (sum, prod), devuelve un tensor de una dimensi´on menos, resultado de realizar la operaci´on sobre la primera dimensi´on:

>> a=zeros(2,3,2); >> a(:,:,1)=[1 2 8; 4 5 6]; a(:,:,2)=[6 2 14; 3 5 1] a(:,:,1) = 1 4

2 5

8 6

2 5

14 1

a(:,:,2) = 6 3

>> max(a)

% 1x3x2

ans(:,:,1) = 4

5

8

ans(:,:,2) = 6

5

14

>> max(max(a)) % 1x1x2 ans(:,:,1) = 8

ans(:,:,2) = 14

>> max(max(max(a))) % 1x1x1, un numero ans = 6 167

´ IV LECCION

8.4 Vectores de celdas

8.4.

Vectores de celdas

r do rra Bo

Aunque los tensores a˜ naden mayor flexibilidad a las matrices y vectores, siguen siendo estructuras r´ıgidas (todas las entradas deben ser n´ umeros reales, a(1,:,:,:) debe tener la misma dimensi´on que a(2,:,:,:),...). Matlab cuenta con una estructura que probablemente sea el paradigma de la flexibilidad en tanto en cuanto permite guardar casi cualquier tipo de dato. Es, por as´ı decirlo, un “caj´on de sastre”. Este tipo de estructura se denomina vector (matriz o tensor) de celdas o cell array. Ya nos hemos encontrado con esta estructura cuando vimos el dise˜ no de funciones cuyo n´ umero de par´ametros de entrada y/o salida era variable. Las variables varargin y varargout son realmente vectores de celdas que conten´ıan distintos tipos de datos a los que se acced´ıa mediante llaves. Un vector de celdas se maneja del mismo. A modo de ejemplo podemos crear un vector de celdas simplemente asignando valores

>> celda={7,[1 2 3;4 5 6],’una cadena de caracteres’,inline(’x+y’)}; >> whos celda Name Size Bytes Class celda

1x4

1214

cell array

Grand total is 95 elements using 1214 bytes

que es equivalente a dar cada una de sus componentes >> >> >> >>

celda{1}=7; celda{2}=[1 2 3;4 5 6]; celda{3}=’una cadena de caracteres’; celda{4}=inline(’x+y’);

Tambi´en se puede proceder, con peque˜ nas diferencias de sintaxis, de la siguiente forma >> celda(1)={7}; >> celda(2)={[1 2 3;4 5 6]};

F´ıjate en la disposici´on de las llaves en los dos ejemplos anteriores. En cualquier caso, una vez definido el vector podemos acceder a cada una de sus componentes indicando entre llaves su posici´on >> celda{1} ans =

7

>> celda{4}([1 2 4], [2 1 1/2]) ans = 3.0000

3.0000

4.5000 168

% funcion!!

´ IV LECCION

Cap´ıtulo 8. Matlab: C´alculo simb´olico y estructuras de datos.

o visualizar todas ellas mediante >> celldisp(celda) celda{1} =

r do rra Bo 7

celda{2} = 1 4

2 5

3 6

celda{3} =

una cadena de caracteres celda{4} =

Inline function: (x,y) = x+y

Este tipo de estructura, aunque muy flexible a la hora de almacenar informaci´on, es sin embargo manejada con menor eficiencia por Matlab, por lo que debe hacerse un uso mesurado de ella. Los comandos varargin y varargout proporcionan un buen ejemplo de una utilizaci´on apropiada de esta estructura.

Ejercicio 8.4 Otra manera de agrupar distintos tipos de datos es utilizar estructuras (“struct”). Una estructura es un tipo de dato del que luego se pueden asignar campos distintos. Por ejemplo, la estructura Libro podr´ıa contener los campos Titulo y Autor que ser´ıan cadenas de caracteres y A~ noPublicacion y NumeroPaginas que ser´ıan n´umeros. Utiliza la ayuda de Matlab para averiguar c´omo pueden definirse estos tipos de datos mediante la orden struct.

169

´ IV LECCION

8.4 Vectores de celdas

r do rra Bo 170

r do rra Bo

Cap´ıtulo 9

C´ alculo num´ erico de valores y vectores propios. 9.1.

Introducci´ on

El estudio de los valores y vectores propios de una matriz surge ligado a una gran cantidad de problemas que se plantean en ´ambitos de muy diversa ´ındole, tales como la Ingenier´ıa, F´ısica, Econom´ıa, Estad´ıstica o Biolog´ıa. Algunos ejemplos los encontramos en el c´alculo de los modos de vibraci´on de algunas estructuras, el estudio de la evoluci´on de sistemas din´amicos, compresi´on de datos, el an´alisis de redes (grafos),... El problema que abordamos es el siguiente: dada una matriz A de tama˜ no n × n queremos encontrar los escalares λ y vectores v 6= 0 que cumplan Av = λv.

Se dice entonces que λ es un valor propio de A y que v es un vector propio asociado a λ. Se trata por tanto de buscar las direcciones invariantes bajo los productos por la matriz. Equivalentemente, los valores propios de A son aquellos valores λ para los que el sistema lineal homog´eneo (A − λI)v = 0, tiene soluciones no nulas, y estas soluciones son los vectores propios asociados a λ. Esta expresi´on nos da una manera de calcular λ: los valores propios son los valores, reales o complejos, para los que A − λI no es invertible, o equivalente, para los que det(A − λI)=0. Concluimos de esta manera que los valores propios son las ra´ıces del polinomio p(λ) := det(A − λI) = 0.

conocido como polinomio caracter´ıstico. Dado que p(λ) tiene grado n, habr´a exactamente n valores propios (aunque alguno de ellos puede estar repetido o ser complejo). Hist´oricamente los m´etodos num´ericos comenzaron trabajando sobre el polinomio caracter´ıstico para hallar los valores propios, pero pronto se comprob´o que este camino no era el m´as indicado. Uno de los hechos que motivaron este abandono radicaba en la inestabilidad num´erica: 171

´ IV LECCION

9.1 Introducci´on

Las ra´ıces de un polinomio son muy sensibles a variaciones en sus coeficientes; El polinomio a su vez puede ser muy sensible a las entradas de la matriz.

r do rra Bo

En vista de lo anterior se plante´o el problema original: ¿son los valores y vectores propios sensibles a peque˜ nas modificaciones de las entradas de la matriz?. Afortunadamente para matrices sim´etricas se tiene la ansiada estabilidad: peque˜ nas variaciones en A, producto por ejemplo de errores de medida o errores de redondeo, dan lugar a peque˜ nas modifica1 ciones en los valores propios . Para matrices arbitrarias este resultado dista mucho de ser cierto, las condiciones para asegurar la estabilidad son m´as complicadas, y podemos encontrarnos con lo que en la terminolog´ıa habitual se denomina, matrices mal condicionadas para el c´alculo de valores propios.

Ejemplo Estas l´ıneas muestran la sensibilidad de una matriz muy simple ante una peque˜ na variaci´on en una entrada. >> a=[149 50 154;-537 -180 -546;27 9 25]; >> p= poly(a) p =

1.0000

6.0000

11.0000

6.0000

>> roots(p).’ ans =

-3.0000

-2.0000

-1.0000

>> b=[149 50 154;-537 -180.01 -546;27 9 25]; >> q=poly(b) ans =

1.0000

6.0100

9.2600

1.6700

>> roots(q).’ ans=

-3.5019

-2.3008

-0.2073



Ejercicio 9.1 Repite el ejemplo anterior con diferentes matrices sim´etricas y observa como el resultado es m´as estable. 1

Probado por primera vez por Hermann Weyl en 1911 en un ´area totalmente distinta.

172

´ IV LECCION

Cap´ıtulo 9. C´alculo num´erico de valores y vectores propios.

´ Nota. Este y otros detalles no eran conocidos en los inicios del c´alculo cient´ıfico. James Hardy Wilkinson relata la siguiente an´ecdota2 . Cuando estaba programando en uno de los primeros ordenadores electr´onicos el m´etodo de Newton para la resoluci´on de ecuaciones no lineales, decidi´o testarlo con el siguiente polinomio (x − 20)(x − 19) · · · (x − 1).

r do rra Bo El m´etodo fallaba de forma reiterada, a pesar de las sucesivas revisiones del c´odigo, hasta que Wilkinson cay´o en la cuenta de que el error no radicaba en su programa sino que las ra´ıces eran tan sensibles num´ericamente que se ve´ıan afectadas por los errores de redondeo. Wilkinson demostr´o que al cambiar el coeficiente de x19 en p, que es −210, por −210 − 2−23 , las ra´ıces 16 y 17 se transforman3 en el par complejo 16.73 ±2.81i. El polinomio en cuesti´on pas´o a la historia del Num´erico con el nombre de “el p´erfido polinomio de Wilkinson”. 

9.2.

Matrices semejantes

Dos matrices A y B son semejantes si existe una matriz P invertible tal que B = P AP −1 .

En este caso,

det(B − λI) = det(P AP −1 − λI) = det(P (A − λI)P −1 ) =

= det(P ) det(A − λI) det(P −1 ) = det(A − λI),

es decir, A y B tienen el mismo polinomio caracter´ıstico y por tanto los mismos valores propios. Este resultado sugiere una estrategia para encontrar los valores propios de A: buscar matrices semejantes para las que el c´alculo de los valores propios sea sencillo. En particular, cuando B es triangular sus valores propios son simplemente los elementos diagonales. Si podemos tomar los n vectores propios linealmente independientes, la matriz P := [v1 |v2 | . . . |vn ] (su i–´esima columna es el vector vi ) es invertible. Entonces AP = P D

⇐⇒

P −1 AP = D,

donde D es una matriz diagonal con los valores propios sobre la diagonal. Si una matriz es semejante a una matriz diagonal se dice que es diagonalizable. Particularmente interesante es el caso en que P se puede tomar adem´as ortogonal. Esto es, P −1 = P > , y por tanto P > AP = D. Las matrices ortogonales son muy estables num´ericamente y posibilitan el dise˜ no de m´etodos m´as robustos frente a errores de redondeo. 2

Recogida por D. Kincaid y W. Cheney en su excelente libro “An´alisis Num´erico: Las Matem´aticas del C´alculo Cient´ıfico.” Addison-Wesley, 1994. 3 ¿C´omo asumir que las ra´ıces de un polinomio tan sencillo fueran imposibles de aproximar por un ordenador? Wilkinson dir´ıa despu´es “Speaking for myself I regard it as the most traumatic experience in my career as a numerical analyst”

173

´ IV LECCION

9.3 M´etodo de potencias

Teorema 9.1 Si A es sim´etrica, existe Q ortogonal tal que Q> AQ = D con D diagonal con los valores propios de A. En particular, los valores propios de una matriz sim´etrica son todos reales.

r do rra Bo

En las Secciones 9.4 y 9.5 de esta lecci´on se estudiar´an dos m´etodos basados en transformaciones de semejanza (producto por matrices ortogonales) que tratan de llevar una matriz sim´etrica a una forma diagonal como forma de calcular los valores propios. Estos m´etodos se pueden adaptar, con m´as o menos ´exito, a matrices arbitrarias llevando en este caso la matriz a una forma triangular o cuasitriangular.

9.3.

M´ etodo de potencias

En esta secci´on presentaremos el m´etodo de potencias y algunas variantes del mismo que proporcionan un valor propio de la matriz. Estos m´etodos combinados con t´ecnicas de deflaci´on, que consisten en construir una nueva matriz con los mismos valores propios que la original salvo el ya el calculado, permiten calcular unos pocos valores propios.

9.3.1.

Descripci´ on del m´ etodo

Asumiremos para empezar que la matriz A tiene un valor propio dominante, es decir, sus valores propios pueden ordenarse en la forma |λ1 | > |λ2 | ≥ |λ3 | ≥ . . . ≥ |λn |.

Supongamos adem´as que tenemos una base formada por vectores propios, esto es podemos tomar {vi }ni=1 vectores propios linealmente independientes (la matriz A es por tanto diagonalizable). Entonces, cualquier vector x0 puede escribirse en la forma x0 =

n X

αi vi

i=1

con αi adecuados. Multiplicando reiteradamente por A obtenemos m

A x0 =

n X

αi λm i vi

=

λm 1





α1 v1 + α2

i=1

λ2 λ1

m



v2 + . . . + αn

λn λ1

m



vn .

(9.1)

Entonces, si α1 6= 0 y m es grande

xm := Am x0 ≈ λm 1 α1 v1 ,

es decir, xm tiende a apuntar en la direcci´on del vector propio asociado al valor propio de mayor m´odulo (en el lenguaje habitual se habla del valor propio dominante). El valor propio λ1 se puede calcular, entre otras posibilidades, mediante el conocido cociente de Rayleigh: x> Axm x> xm+1 (m) λ1 := m 2 = m 2 ≈ λ1 . kxm k kxm k 174

´ IV LECCION

Cap´ıtulo 9. C´alculo num´erico de valores y vectores propios.

Proposici´ on 9.2 Bajo las hip´otesis anteriores (m)

= λ1 + O

(m)

= λ1 + O

λ1 Si adem´as A es sim´etrica

λ1 λ2

.

  2m  λ1 λ2

.

r do rra Bo

λ1

  m 

Basado en estas ideas surge el m´etodo de potencias, que simplemente consiste en multiplicar un vector inicial por las potencias sucesivas de la matriz A. Para evitar que los vectores xm tengan componentes muy grandes o muy peque˜ nas se genera una sucesi´on de vectores normalizados, es decir, una vez multiplicado por A se procede a dividir por su norma. El algoritmo es el siguiente: M´ etodo de potencias 01

x0 6= 0

02

y0 =

03

for m=1:mmax

vector inicial

x0 kx0 k2

04

xm = Aym−1

05

> xm λ(m) = ym−1 xm ym = kxm k2

06

07

if kym − ym−1 k2 < eps

08 09 10

end

return

end

La l´ınea 06 es simplemente el cociente de Rayleigh que, como la norma escogida para normalizar es la eucl´ıdea, adopta esta expresi´on m´as sencilla. Hemos elegido como criterio de parada la diferencia entre dos vectores consecutivos. Otra posible elecci´on es |λ(m) − λ(m−1) | < eps |λ(m) |. Ejercicio 9.2 Programa el m´etodo de potencias

Soluci´ on. He aqu´ı una implementaci´on del m´etodo. 01 02 03

%POTENCIAS % %LB=POTENCIAS(A)

Devuelve en LB una aproximacion del 175

´ IV LECCION

9.3 M´etodo de potencias % % % %[LB,V]=POTENCIAS(A) % %[LB,V,NITER]=POTENCIAS(A) % % LB=POTENCIAS(A,MMAX) % % LB=POTENCIAS(A,MMAX,EPS) % % LB=POTENCIAS(A,MMAX,EPS,V0)

mayor valor propio de A calculado por el metodo de potencias V es el vector propio NITER son las iteraciones calculadas

r do rra Bo

04 05 06 07 08 09 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46

MMAX

No. maximo de iteraciones n

EPS es el criterio de parada

V0 vector inicial para la iteracion

function [lb,x,m]=potencias(a,varargin); n=length(a); if nargin>1 & ~isempty(varargin{1}) mmax=varargin{1}; else mmax=n*2; end if nargin>2 & ~isempty(varargin{2}) eps=varargin{2}; else eps=1e-6; end if nargin>3 & ~isempty(varargin{3}) y=varargin{3}; else y=rand(n,1); end y=y/norm(y);

for m=1:mmax x=a*y; lb=y’*x; x=x/norm(x); if norm(x-y)> [lb,v]=potencias(a,[],[],v0);

% especifico el vector inicial 

r do rra Bo

Ejercicio 9.3 Compara la velocidad de convergencia y el n´umero de iteraciones requerido para distintas tolerancias y vectores iniciales al tomar las matrices       −1 −3 0 −1 −3 0 −1 4 −2 9 4 , 9 4 , 9 −1  . A= 4 B =  −3 C= 4 −2 −1 5 0 4 5 −2 −1 5

Nota. Cuando no se conoce una aproximaci´on del vector propio asociado al valor propio dominante, se suele iniciar el algoritmo partiendo de un vector generado aleatoriamente. Podr´ıa ocurrir que para el vector inicial α1 = 0, pero la probabilidad de que se d´e este problema es (pr´acticamente) nula. En este caso, si |λ2 | > |λ3 |, salvo por errores de redondeo4 , el m´etodo proporcionar´a el valor propio subdominante λ2 y su vector propio asociado normalizado. No es necesario que la matriz sea diagonalizable para que el m´etodo de potencias converja. Tampoco que el subespacio asociado al valor propio dominante est´e generado por un u ´nico vector. En este caso, que s´olo puede darse si λ1 es un valor propio repetido, el m´etodo puede converger a distintos vectores propios normalizados dependiendo del vector inicial considerado. Si |λ1 | = |λ2 |, es decir, λ1 = ±λ2 ´o λ1 y λ2 son n´ umeros complejos conjugados, entonces el m´etodo de potencias falla.  Ejercicio 9.4 Consideremos la matriz 

0  1 A=  0 0

0 0 1 0

 0 −24 0 50   0 −35  1 10

cuyos valores propios son 1, 2, 3 y 4.

1. Aplicar el m´etodo de potencias a la matriz A partiendo de un vector aleatorio y del vector (−20, 33, −15, 2)> .

2. Sabiendo que v1 = (−24, 26, −9, 1)> y v2 = (−12, 19, −8, 1)> son vectores propios asociados a los valores propios 1 y 2 respectivamente, ¿qu´e crees que ocurrir´a si se toma como vector inicial v1 − 3v2 = (12, −31, 15, −2)> ? 3. Observa para distintas tolerancias la diferencia entre partir del vector del apartado anterior y de (12, −31, 15, −2.0001)> .

4

El efecto de los errores de redondeo se traduce en una componente no nula en la direcci´on de v1 , incluso aunque el vector inicial no la tuviese. Se podr´ıa decir que ´este es uno de los pocos casos en los que los errores de redondeo nos pueden ayudar.

177

´ IV LECCION

9.3 M´etodo de potencias

Ejercicio 9.5 En este ejercicio vamos a comprobar que el c´alculo de los valores propios utilizando el polinomio caracter´ıstico no es el camino correcto. Teclea las instrucciones en un fichero script

r do rra Bo

n=50; d=1/n:1/n:1; [q,r]=qr(rand(n)); a=q’*d*q;

En a tenemos una matriz sim´etrica con valores propios5 {0.02, 0.04, 006, . . . , 1}. Se trata de que apliques potencias para calcular el valor propio dominante y compares el resultado con el que obtienes al calcular las ra´ıces del polinomio caracter´ıstico. Compara los resultados. Cambia el valor de n y observa el efecto que tiene en matrices cada vez m´as grandes.

9.3.2.

Variantes del m´ etodo de potencias

M´ etodo de la potencia inversa

Si A es invertible y v es un vector propio asociado a un valor propio λ (que ser´a distinto de cero), entonces, Av = λv ⇐⇒ A−1 v = λ−1 v. Es decir, λ−1 es un valor propio de la matriz inversa y v es un vector propio asociado. Por tanto podemos aplicar el m´etodo de potencias a la matriz A−1 para calcular el menor valor propio en valor absoluto de A. En lugar de calcular el producto xm = A−1 ym−1 (l´ınea 04 en el m´etodo de potencias) resolveremos en cada iteraci´on el sistema6 Axm = ym−1 .

Disponemos para ello de una galer´ıa amplia de m´etodos vistos en las Lecciones I y II. Notemos adem´as que en cada iteraci´on se tiene que resolver un sistema cuya matriz es siempre la misma, as´ı que si optamos por un m´etodo directo podemos calcular la factorizaci´on LU una u ´nica vez, fuera del bucle for (l´ıneas 03--10), y resolver de forma reiterada los dos sistemas triangulares. Si por contra se opta por un m´etodo iterativo, podemos arrancar el esquema utilizando xm−1 , la aproximaci´on del vector propio calculada en la iteraci´on anterior. Ejercicio 9.6 Programa a partir del Ejercicio 9.2 el algoritmo de la potencia inversa.

M´ etodo de potencias desplazado

Si λ es un valor propio de A, entonces λ − α es un valor propio de A − αI y (λ − α)−1 lo es de (A − αI)−1 . Por tanto, si aplicamos el m´etodo de potencias a la matriz A − αI

5

El comando qr descompone A = QR con Q ortogonal y R triangular. Por tanto los valores propios de Q> AQ coinciden con los de A. La Secci´on 9.5.1 est´a dedicada al c´alculo de esta descomposici´on. 6 Recuerda que invertir una matriz para multiplicarla posteriormente por un vector es mucho m´as costoso que resolver el sistema correspondiente.

178

´ IV LECCION

Cap´ıtulo 9. C´alculo num´erico de valores y vectores propios.

donde α es una constante conocida, podemos obtener el valor propio de A m´as alejado de α. M´as interesante desde el punto de vista pr´actico es aplicar el m´etodo de potencias a (A − αI)−1 , que nos proporcionar´a el valor propio de A m´as pr´oximo a α.

r do rra Bo

Ejercicio 9.7 Modifica el programa del Ejercicio 9.6 para implementar el m´etodo de potencias desplazado. Los argumentos obligatorios de entrada ser´an ahora A y alpha.

Comentarios finales

El m´etodo de potencias tiene una ventaja evidente: su simplicidad. Ni siquiera necesitamos la matriz en s´ı, s´olo saber multiplicar por ella. El algoritmo de la potencia desplazada se puede utilizar para el c´alculo de un vector propio si se conoce λ, el valor propio asociado. Basta para ello aplicar el m´etodo con α = λ +  con  . Mediante > ARpq A1 := Rpq

(p, q y α adecuados) vamos a anular el mayor elemento extradiagonal de A. Esta operaci´on (1) s´olo afecta a las filas y columnas p, q de A. Concretamente, si denotamos por aij las entradas de A1 , a(1) = (aqq − app ) cos α sen α + apq (cos2 α − sen2 α) = pq =

1 (aqq − app ) sen(2α) + apq cos(2α). 2

Por tanto, el ´angulo α debe tomarse de modo que  si aqq = app ,   cos(2α) = 0, 2apq  , en caso contrario.  tan(2α) = aqq − app

Para calcular cos α y sen α evitando el uso de un arcotangente se recurre a algunas manipulaciones trigonom´etricas que prueban que si7 θ :=

aqq − app , 2apq

entonces

cos α = √

t :=

1 , t2 + 1

sign(θ) √ , |θ| + θ2 + 1

sen α = √

t . t2 + 1

Cuando aqq = app tomamos

1 cos α = √ , 2

7

sen αm =

−sign(aqq ) √ . 2

sign (z) es el signo de z, −1 si z es negativo, 1 en caso contrario.

180

´ IV LECCION

Cap´ıtulo 9. C´alculo num´erico de valores y vectores propios.

r do rra Bo

El m´etodo ya se vislumbra en este estado: se trata de repetir el mismo argumento con A1 para obtener una segunda matriz A2 resultado de cancelar el mayor elemento extradiagonal de A1 . De esta forma, reiterando este proceso llegamos a una sucesi´on de matrices Am que cumplen   λ1   λ2   Am −→ D :=  cuando m → ∞. , . .   . λn

Adem´as, definiendo Qm := Rp1 q1 (α1 )Rp2 q2 (α2 ) . . . Rpm qm (αm ), donde Rpk ,qk es la matriz utilizada en el paso k−´esimo Q−1 m AQm = Am −→ D.

Por tanto, las columnas de Qm son las aproximaciones (ortonormales) de los vectores propios correspondientes. El siguiente teorema prueba la convergencia de este m´etodo. Para ello necesitamos la llamada norma de Frobenius8 kAkF :=

n hX

2

|ai,j |

i1/2

i,j=1

Teorema 9.3 Sea Am la matriz en la iteraci´on m, Dm su diagonal y Bm := Am − Dm . Entonces 2 kAm kF = kAm+1 kF , kBm+1 k2F = kBm k2 − 2|a(m) pm qm |

El resultado dice en primer lugar que la norma de Frobenius de una matriz no cambia cuando se multiplica a izquierda y derecha por las matrices Rpq (α), una de ellas traspuesta. De hecho se preserva cuando se multiplica, a izquierda y derecha, por matrices ortogonales arbitrarias. El segundo resultado dice algo m´as: el peso de los elementos extradiagonales disminuye en cada paso seg´ un el elemento cancelado. Esto asegura la convergencia del proceso hasta obtener una matriz diagonal. En la pr´actica, el proceso se interrumpe cuando los elementos que est´an fuera de la diagonal son suficientemente peque˜ nos. En concreto, se suele tomar el siguiente criterio de parada !1/2 n X (m) |a(m) |aii |2 . pm qm | < eps i=1

F´ıjate que las matrices Am y Am+1 s´olo difieren en las filas y columnas pm y qm . A efectos pr´acticos no ser´a necesario formar las matrices de rotaci´on ya que basta conocer los valores de cos αm y de sen αm para construir Am+1 a partir de Am .

Ejercicio 9.8 Implementa el m´etodo de Jacobi. 8

En Matlab ser´ıa norm(a(:)) o norm(a,’fro’).

181

´ IV LECCION

9.4 M´etodo de Jacobi

Soluci´ on. La parte central del programa se puede implementar con las siguientes l´ıneas % % % % % % % % % % % % % % %

JACOBI D=JACOBI(A)

Aplica el metodo de Jacobi a A y devuelve en D los valores propios; A debe ser simetrica

r do rra Bo

01 02 03 04 05 06 07 08 09 10 11 12 13 14 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41

[D,Q]= JACOBI(A)

Q es ortogonal con Q’A Q=D

[D,Q,NITER]= JACOBI(A)

NITER Numero de iteraciones calculadas

D=JACOBI(A,NMAX)

NMAX numero maximo de iteraciones

D=JACOBI(A,NMAX)

NMAX numero maximo de iteraciones

D=JACOBI(A,NMAX,EPS)

EPS es el criterio de parada

function [d,Q,m]= jacobi(a,varargin) n=length(a); if nargin>1 & ~isempty(varargin{1}) mmax=varargin{1}; else mmax=n^2; end if nargin>2 & ~isempty(varargin{2}) eps=varargin{2}; else eps=1e-5; end

Q=eye(n); for m=1:mmax d=diag(a); %Calculo del mayor elemento extradiagonal [max1,p]=max(abs(a-diag(d))); [max2,q]=max(max1); p=p(q); if max2 a=rand(120); a=a+a’;

y activamos el profile de Matlab con >> profile on

Ahora Matlab va a llevar un control sobre el tiempo que consume cada l´ınea de c´odigo9 . A continuaci´on ejecuta el programa jacobi para a con un n´ umero m´aximo de iteraciones suficientemente alto de forma que asegures convergencia. La instrucci´on >> profile report

despliega un informe donde puedes ver el tiempo que ha consumido cada parte del programa. Se observa claramente que las l´ıneas m´as costosas son aqu´ellas empleadas en la b´ usqueda del m´aximo elemento extradiagonal (observa la Figura 9.1). Es precisamente 183

´ IV LECCION

9.4 M´etodo de Jacobi

r do rra Bo

MATLAB Profile Report: Function Details jacobi

C:/Documents and Settings/Víctor/Escritorio/LibroMatlab/jacobi.m

Time: 14.75100000 s (100.0%) Calls: 1 Self time: 14.75100000 s (100.0%) Function: Time jacobi

Calls Time/call

14.75100000

1 14.75100000

Parent functions: none

Child functions: none

99% of the total time in this function was spent on the following lines: 33: for m=1:mmax

0.07643962 1% 34: 35:

13.37100000 91% 36: 0.26000000 2% 37: 38:

0.07000000 0% 39:

d=diag(a);

%Calculo del mayor elemento extradiagonal [max1,p]=max(abs(a-diag(d))); [max2,q]=max(max1);

p=p(q);

if max2
View more...

Comments

Copyright ©2017 KUPDF Inc.
SUPPORT KUPDF