Archives du mot-clé conseils

Gérez la compatibilité descendante de vos codes MATLAB

MathWorks publie deux versions de MATLAB par an avec à chaque fois son lot de nouvelles fonctions. La version R2014b est attendue prochainement.

Si vous souhaitez diffuser vos programmes à un maximum d’utilisateurs, vous devez veillez à la compatibilité descendante (ou rétrocompatibilité) de vos codes. C’est à dire que vous devez prendre en compte le fait que certains utilisateurs ont une version moins récente de MATLAB que la vôtre.

Deux questions se posent alors :

  • jusqu’à quelle version de MATLAB assurer la compatibilité ?
  • comment déterminer ce qui casse la compatibilité descendante ?

Quelle version de MATLAB ?

Vous vous en douterez, il n’y a pas de réponse précise à cette question… Nous avons ouvert plusieurs sondages sur le forum MATLAB :

Au passage, vous pouvez toujours participer au sondage de 2014 !

En voici les résultats :

Versions utilisateurs MATLAB 2013

Sondage 2013

Versions utilisateurs MATLAB 2014

Sondage 2014

Malgré le peu de votes, on peut juger que la compatibilité devrait être gérée jusqu’aux versions R2011.

Comment déterminer ce qui casse la compatibilité descendante ?

La solution la plus efficace est d’installer la version la plus ancienne de MATLAB pour laquelle vous souhaitez assurer la compatibilité sur votre machine de développement. Votre licence MATLAB vous permet d’installer les versions plus anciennes.

A l’exécution du code, en cas de problème de compatibilité, vous rencontrez surement l’erreur Undefined function or variable ‘***’. Dans ce cas, vous devrez alors écrire un code alternatif pour gérer l’absence de cette fonctionnalité. Vous pourrez alors utiliser la fonction verLessThan présentée ci-dessous.

Si vous ne pouvez pas installer une ancienne version, il faudrait alors faire la liste de tous les changements répertoriés dans les Release Note des versions de MATLAB (voir la FAQ Où trouver la documentation des différentes versions de MATLAB en ligne ?). Tout ça risque d’être assez laborieux. Vous pouvez consulter une liste partielle de ces changements sur ce site : MatlabVersionsCompatibility.

La fonction verLessThan

La fonction verLessThan permet de tester si la version de MATLAB en cours d’utilisation est antérieure à une version donnée. Pour les numéros de version, voir la deuxième colonne du tableau donné dans la FAQ : Quelles sont les différentes versions de MATLAB ?

Prenons le cas de la fonction strjoin ajoutée avec la version R2013a (8.1) de MATLAB. Une version antérieure de MATLAB ne pourra pas l’exécuter. Vous devrez donc pas exemple écrire votre propre fonction mystrjoin et faire le teste suivant dans le code :

if verLessThan('matlab', '8.1')
    B = mystrjoin(A, ',');
else
    B = strjoin(A, ',');
end

Conclusion

Comme vous l’aurez compris, il est difficile d’assurer une compatibilité parfaite d’un code MATLAB récent avec des versions plus anciennes. J’espère au moins vous avoir sensibilisé à ce problème.

Deux conseils pour finir :

  • spécifiez la version de MATLAB que vous avez utilisée dans l’entête de votre code
  • laissez également un email pour permettre aux utilisateurs de vous contacter

A quoi sert la fonction « length » de MATLAB ?

Je lis régulièrement des codes MATLAB où la fonction length est utilisée.

Pour ma part, je ne l’utilise jamais.

Pourquoi donc ?

La fonction « length »

Comme son nom l’indique la fonction length renvoie une longueur, dans le sens d’une dimension d’un tableau.

Pour un vecteur, c’est assez évident :

>> V = [1 9 4 8 7];
>> length(V)

ans =

     5

Mais qu’en est-il pour un tableau ?

Prenons un cas simple :

>> M = rand(4,3);
>> length(M)

ans =

     4

Permutons les dimensions du tableau :

>> M = rand(3,4);
>> length(M)

ans =

     4

Et oui, voici ce que dit la documentation :

[length] finds the number of elements along the largest dimension of an array

Le résultat correspond bien, dans les deux cas, au nombre d’éléments le long de la plus grande dimension du tableau.

Les fonctions similaires

Les autres fonctions permettant de récupérer des informations sur les dimensions d’un tableau sont :

  • size : nombre d’éléments selon une des dimensions du tableau
  • numel : nombre total d’éléments du tableau

C’est celles que j’utilise tout le temps car il n’y a pas d’ambiguïté dans les informations qu’elles renvoient.

A quoi sert donc la fonction « length » ?

Bien entendu, je comprends le fonctionnement de la fonction length comme dans l’exemple de la documentation :

>> Y = rand(2, 5, 17, 13);
>> length(Y)

ans =

    17

Mais je n’arrive pas à trouver une application où il serait utile de connaitre le nombre d’éléments présents le long de la plus grande dimension d’un tableau.

Si vous avez des idées, n’hésitez pas à les partager ;)

Peut-on utiliser « i » comme indice de boucle dans MATLAB ?

La question peut sembler bizarre pour la plupart des développeurs, surtout ceux qui ne codent pas avec MATLAB.

« i » comme indice de boucle

La variable « i » est couramment utilisée pour désigner l’indice des boucles en programmation informatique.

En C :

for(i=0;i<10;i++)
   printf("%d\n", i);

En Fortran :

do i=0,9
   print*,i
end do

Avec MATLAB :

for i = 0:9
   fprintf("%d\n", i);

Mais pourquoi utilise-t-on « i » au fait ? Certains y voient un héritage des notations mathématiques, d'autres du Fortran, ou alors un peu des deux, ou encore que « indice » et « index » commencent par i. Il n'y a, semble-t-il, pas de réponse absolue. Lire à ce sujet : Why are variables “i” and “j” used for counters?

« i » pour désigner les nombres complexes avec MATLAB

MATLAB est un outil initialement conçu pour le calcul numérique. A ce titre, il prend en compte les nombres complexes (et les calculs associés) depuis sa première version.

Hobbes explique les nombres imaginaires à Calvin

Pour définir une valeur complexe, on utilise la syntaxe suivante :

>> cmplx = 1 + 3i

cmplx =

   1.0000 + 3.0000i

Le caractère « i » est obligatoirement placé après la valeur numérique de la partie imaginaire, sans aucun espace.

Sinon :

>> cmplx = 1+i3
Undefined function or variable 'i3'.

>> cmplx = 1 + 3 i
 cmplx = 1 + 3 i
              |
Error: Unexpected MATLAB expression.

Nombres complexes et boucle avec MATLAB

Pour mettre en évidence l’ambiguïté entre ces deux utilisations de « i », prenons un exemple simple :

for i = 1:4
    X(1,i) = 1+3*i;      
    Y(1,i) = 1+3i;    
end

Les variables X et Y contiennent-elles toutes les deux des valeurs complexes ?

Affichons leur contenu :

X =

     4     7    10    13


Y =

   1.0000 + 3.0000i   1.0000 + 3.0000i   1.0000 + 3.0000i   1.0000 + 3.0000i

Dans ce cas, X contient donc uniquement des valeurs réelles.

Que ce passe-t-il si on supprime la variable i et que l’on renomme la variable qui incrémente la boucle ?

clear i

for n = 1:4
    X(1,n) = 1+3*i;      
    Y(1,n) = 1+3i;    
end

Voici le contenu de X et Y :

X =

   1.0000 + 3.0000i   1.0000 + 3.0000i   1.0000 + 3.0000i   1.0000 + 3.0000i


Y =

   1.0000 + 3.0000i   1.0000 + 3.0000i   1.0000 + 3.0000i   1.0000 + 3.0000i

Aïe… les deux codes ont quasiment la même syntaxe, mais ne donnent pas du tout le même résultat !

Solution

Certains préconisent de ne jamais employer « i » comme indice de boucle. Oui pourquoi pas. Pour ma part, je ne suis convaincu par aucun dogme (MATLAB c’est mal…)

Pourquoi devrais-je donc impérativement ne pas utiliser « i » comme variable d’incrément dans mes codes ?

Il est vrai que j’utilise souvent « n », mais je ne saurais réellement dire pourquoi, si ce n’est par habitude. En traitement d’images, j’utilise parfois « r » et « c » pour désigner respectivement les lignes (rows) et les colonnes (columns) pour parcourir les pixels d’une image.

Solution robuste

Il y a en fait deux façons de créer un nombre complexe avec MATLAB, celle que l’on a vue précédemment et celle qui consiste à utiliser la fonction complex :

>> cmplx = complex(1,3)

cmplx =

   1.0000 + 3.0000i

Dans ce cas, aucune ambiguïté, ni aucune chance pour que la définition du nombre complexe n’entre en conflit avec une variable i définie préalablement dans le code.

La fonction complex est également utile quand la partie imaginaire du nombre complexe est nulle.

En effet :

>> cmplx = 1+0i

cmplx =

     1

>> isreal(cmplx)

ans =

     1

Alors que :

>> cmplx = complex(1,0)

cmplx =

     1

>> isreal(cmplx)

ans =

     0

La première syntaxe renvoie une variable contenant une valeur réelle alors que la deuxième syntaxe renvoie une valeur complexe.

Conclusion

L’emploi du caractère « i » peut être source de confusion et d’erreur dans la syntaxe et l’exécution de code MATLAB.

Il n’y a pas de solution parfaite, mis à part l’utilisation de la fonction complex.

Dans tous les cas, c’est à vous, développeurs, de déterminer si l’ambiguïté peut apparaitre dans votre code et de la prendre en compte si besoin.

PS : ce billet fait suite à une remarque de tachmou dans la discussion Probleme incrementation boucle for du forum MATLAB.