Compatibilidad entre MATLAB y Octave
Aunque Octave es un proyecto que evoluciona de manera independiente a MATLAB, el proyecto Octave mantiene un alto nivel de compatibilidad con MATLAB, por lo que en general es sencillo pasar de MATLAB a Octave. En el caso de Octave UPM, la migración es todavía más sencilla, pues está adaptado para que la similitud con MATLAB sea incluso mayor que en el caso de Octave. Pero a pesar de todo esto, la compatibilidad no es completa.
En esta página mantenemos una lista de los problemas de compatibilidad entre MATLAB y Octave. El enfoque es que nos gustaría emplear Octave para crear código que se ejecute sin problema en MATLAB (además de Octave, claro). El proyecto Octave mantiene una página sobre cómo portar código de MATLAB a Octave, explicando algunas diferencias, es decir, las diferencias están explicadas desde la perspectiva de alguien que viene de MATLAB y quiere ejecutar su código en Octave. Nuestro objetivo aquí es diferente: se trata de escribir código en Octave, que se pueda ejecutar en MATLAB y Octave.
Sobre cómo usar MATLAB y Octave indistintamente, solventando los posibles problemas de compatibilidad, además de esta página puedes consultar los materiales de Guillem Borrell, de la ETS de Ingeniería Aeronáutica de la UPM, que incluye además vídeos de cursos de MATLAB que se han enseñado usando Octave.
Aunque existe una opción en la configuración en Octave UPM para que se emita un aviso cada vez que se realice una operación que no es compatible con MATLAB, y algunas operaciones específicas se pueden configurar en Octave UPM desde la versión R6, existen muchos casos en los que no se emitirá el aviso, incluso si la operación realizada no es compatible con MATLAB. Con el objetivo de mejorar la compatibilidad entre Octave y MATLAB, en esta página recogemos una lista de estos ejemplos.
Índice
Operaciones con int
y single
En MATLAB, las variables tipo int
solo pueden realizar operaciones
aritméticas con variables int
de la misma clase (por ejemplo, int8
con int8
), y con variables tipo double
. Si se intenta realizar una
operación int8
con single
, MATLAB produce un error, sin embargo,
Octave no produce ningún error.
Veamos un ejemplo en MATLAB
>> a = int8(2); >> b = single(3); >> a+b Error using + Integers can only be combined with integers of the same class, or scalar doubles.
El mismo ejemplo con Octave
>> a = int8(2); >> b = single(3); >> a+b ans = 5 >> whos Variables in the current scope: Attr Name Size Bytes Class ==== ==== ==== ===== ===== a 1x1 1 int8 ans 1x1 1 int8 b 1x1 4 single Total is 3 elements using 6 bytes
Como vemos, al operar el resultado es de tipo int8
. Es decir, en lo
que respecta a las operaciones con enteros, en Octave, tanto single
como double
pueden operar con variables de tipo int
, mientras que
en MATLAB solo se permite con double
.
Suma de matrices de diferentes dimensiones
En MATLAB, solo se pueden sumar matrices de las mismas dimensiones, y cualquier diferencia en las dimensiones, provocará un error.
Sin embargo, en Octave, al realizar una suma de matrices de
dimensiones diferentes, Octave intentará realizar broadcasting, que
básicamente significa que extenderá la matriz más pequeña, repitiendo
filas y/o columnas, hasta que tenga las dimensiones necesarias para
poder realizar la operación. El broadcasting solo se aplica cuando
alguna de las dos dimensiones (filas o columnas) es igual a 1
. Es
decir, solo se aplica cuando combinamos matrices con vectores, tanto
vectores fila como columna.
Al realizar broadcasting, Octave emite un aviso. En la versión R6 y posteriores de Octave UPM, depende de cómo tengamos configurada la opción en la pestaña de "Compatibilidad", veremos el "warning", no lo veremos, o incluso veremos cómo se produce un error al intentar realizar la operación. Pero en Octave, por defecto, muestra un mensaje de warning.
Veamos un ejemplo en MATLAB:
>> A = rand(3); >> B = rand(3,1); >> A+B Error using + Matrix dimensions must agree.
El mismo ejemplo en Octave:
>> A = rand(3); >> B = rand(3,1); >> A+B warning: operator +: automatic broadcasting operation applied ans = 1.46679 1.64694 1.25404 1.33553 1.25975 1.03132 1.01001 1.50865 1.06596
¿Cómo hacer que Octave tenga el mismo comportamiento que MATLAB?
En Octave UPM R6 y posteriores, podemos ir a la configuración, pestaña "Compatibilidad", y seleccionar "Lanzar un error (no permitir)" para las operaciones de broadcasting.
En Octave, en general, podemos transformar cualquier mensaje de aviso en un error. En este caso, si cambiamos el aviso de broadcasting, el comportamiento será el mismo que en MATLAB:
>> warning ("error", "Octave:broadcast"); >> A+B error: operator +: automatic broadcasting operation applied
Formatear números en sprintf
con %d
Cuando estamos formateando cadenas de texto que incluyen números,
usando sprintf, el delimitador %d
se emplea para números enteros. En
Octave, en el caso de números con parte decimal, solo se mostrará la
parte entera del número.
Sin embargo, en MATLAB, si el número tiene parte decimal, se mostrará
en notación científica. Esto es quizás un error en MATLAB, pues la
notación científica se especifica con %e
.
Veamos tres ejemplos. Primero, en MATLAB:
>> sprintf('Prueba %d', 1) ans = Prueba 1 >> sprintf('Prueba %d', 1.123456) ans = Prueba 1.123456e+00 >> sprintf('Prueba %e', 1.123456) ans = Prueba 1.123456e+00
Los mismos ejemplos en Octave:
>> sprintf('Prueba %d', 1) ans = Prueba 1 >> sprintf('Prueba %d', 1.123456) ans = Prueba 1 >> sprintf('Prueba %e', 1.123456) ans = Prueba 1.123456e+00
Como vemos en el segundo caso, en Octave, sprintf con un número
decimal usando %d%
solo muestra la parte entera. En cambio, en
MATLAB, el resultado es el mismo usando %d
y %e
con un número
decimal.
En el caso de números sin parte decimal, el comportamiento es el mismo en ambos casos.
Esta diferencia también afecta a la función fprintf
.
Dibujar funciones con fplot
Imaginemos que tenemos la siguiente función f(x)
function y = f(x) y = x^3
Esta función se puede dibujar en MATLAB directamente usando el comando fplot
>> fplot('f', [-2,2])
Sin embargo, en Octave obtenemos un error
>> fplot('f',[-2,2]) error: for A^b, A must be a square matrix
Es decir, en MATLAB el comando fplot
no asume que la función puede
trabajar elemento a elemento, y en vez de pasar un vector de valores
de x
, pasa cada uno de los valores individualmente. Esto no ocurre
en Octave, que para dibujar con fplot
pasa un vector de valores de
x
, por lo que la función debe trabajar elemento a elemento para
poder usar fplot para representarla.
Función TriScatteredInterp
Esta función no está todavía disponible en Octave. En este informe de fallo hay comentarios explicando cómo lograr el mismo comportamiento usando otras funciones disponibles en Octave.