MATLAB
Scripts et fonctions
Instructions de contrle
o Boucle FOR : parcours d'un intervalle
o Boucle WHILE : tant que . . . faire
o L'instruction conditionne IF
o Choix ventil, l'instruction switch
o Interruption d'une boucle de contrle
Un exemple complet
Scripts et fonctions
Il est possible d'enregistrer une squence d'instructions dans un fichier (appel un M-file ) et
de les faire excuter par MATLAB. Un tel fichier doit obligatoirement avoir une extension de
la forme .m (d'o le nom M-file) pour tre considr par MATLAB comme un fichier
d'instructions. On distingue 2 types de M-file, les fichiers de scripts et les fichiers de
fonctions. Un script est un ensemble d'instructions MATLAB qui joue le rle de programme
principal. Si le script est crit dans le fichier de nom nom.m on l'excute dans la fentre
MATLAB en tapant nom. Mme si l'on ne souhaite pas proprement parler crire de
programme, utiliser un script est trs utile. Il est en effet beaucoup plus simple de modifier
des instructions dans un fichier l'aide d'un diteur de texte que de retaper un ensemble
d'instructions MATLAB dans la fentre de commande.
Les fichiers de fonctions ont deux rles. Ils permettent l'utilisateur de dfinir des fonctions
qui ne figurent pas parmi les fonctions incorpores de MATLAB (<< built-in functions >>) et de
les utiliser de la mme manire que ces dernires (ces fonctions sont nommes fonctions
utilisateur). Ils sont galement un lment important dans la programmation d'applications
o les fonctions jouent le rle des fonctions et procdures des langages de programmation
usuels.
On dfinit la fonction fonc de la manire suivante:
function [vars1, ..., varsm] = fonc(vare_1, ..., varen)
squence d'instructions
squence d'instructions
Le fichier doit imprativement commencer par le mot-cl function. Suit entre crochets les
variables de sortie de la fonction, le symbole =, le nom de la fonction et enfin les variables
d'entre entre parenthses. Si la fonction ne possde qu'une seule variable de sortie, les
crochets sont inutiles. Il est impratif que la fonction ayant pour nom fonc soit enregistre
dans un fichier de nom fonc.m sans quoi cette fonction ne sera pas << visible >> par MATLAB.
Dans l'exemple qui suit, on dfinit une fonction modulo qui calcule la valeur de a modulo n en
prenant pour systme de rsidus {1, 2, ..., n} au lieu de {0, 1, ..., n-1} (systme de rsidus
considr par la fonction incorpore mod). Les lignes qui suivent doivent tre enregistres
dans un fichier de nom modulo.m.
function [r,q] = modulo(a,n)
%
%
%
%
%
%
%
%
q = floor(a./n);
r = a - n*q;
% si le reste de la division entiere vaut 0, le residu vaut par convention
n
if r == 0, r = n; end
Les lignes prcdes du symbole % sont des lignes de commentaire. Les lignes de
commentaire situes entre la ligne function ... et la 1-ere ligne d'instructions sont affiches
si l'on demande de l'aide sur la fonction modulo.
>> help modulo
L'appel d'une fonction utilisateur s'effectue de la mme faon que l'appel de n'importe quelle
fonction MATLAB:
>> b = 10 ; m = 4;
>> [r,q] = modulo(b,m)
r =
2
q =
2
>> modulo(10,5)
ans =
5
>>
Remarques:
1. Il n'y a pas de mot-cl (par exemple end) pour indiquer la fin de la fonction. La
fonction est suppose se terminer la fin du fichier. Il est toutefois possible de
provoquer un retour au programme appelant dans le corps de la fonction grce la
commande return.
2. On ne peut crire qu'une seule fonction par fichier (qui doit porter le nom de cette
fonction). Toutefois dans la version 5 de MATLAB existe la notion de << sous-fonction
>>. Une sous-fonction est une fonction crite dans le mme fichier qu'une autre
fonction (dite principale) et qui ne sera utilisable que par cette fonction principale (une
sous-fonction ne peut pas tre appele par un autre sous-programme que la fonction
principale).
3. Si le fichier ne commence pas par le mot-cl function on a tout simplement crit un
script!
La gestion des variables d'entre et de sortie est trs souple sous MATLAB. Si l'on n'est
intress que par le rsidu et pas par le quotient, on peut se contenter de ne mettre qu'une
seule variable de sortie, v = modulo(10,4). Dans cet appel la variable v contiendra le
rsidu (la premire variable de sortie). Par contre, mme si l'on ne souhaite recueillir que le
quotient, on est oblig d'effectuer un appel de la forme [r,q] = modulo(10,4) et donc
de dfinir une variable inutile. Aussi, d'une manire gnrale, il est bon de ranger les variables
de sortie par ordre << d'importance >>. Il est galement possible d'appeler une fonction donne
avec moins de variables d'entre que le nombre indiqu pour la dfinition de la fonction (il
faut bien entendu que le corps de la fonction soit programm de sorte de prvoir cette
ventualit). Il existe deux fonctions MATLAB utiles pour grer cette situation: nargin qui
retourne le nombre de variables d'entre utiliss lors de l'appel et nargout qui retourne le
nombre de variables de sortie prvues lors de l'appel. Voici un petit exemple venant illustrer
ces possibilits.
function [A,rang] = matale(T,m,n)
%
%
%
%
%
%
%
%
%
%
%
=
=
=
=
Matale(T,m,n)
Matale(T,m)
Matale(T,m,n)
Matale(T,m)
if nargin == 2
A = fix(T*rand(m));
else
A = fix(T*rand(m,n));
end
if nargout == 2
rang = rank(A);
end
Dans cet exemple, on gre les variables d'entre de la fonction de sorte de ne pas avoir besoin
de donner lors de l'appel le nombre de lignes et de colonnes si la matrice est carre. On gre
aussi les variables de sortie afin de ne pas calculer le rang de la matrice si aucune variable de
sortie pour le rsultat n'est prvue lors de l'appel.
>> [A,r] = matale(20,3,4)
A =
16
13
13
10
10
16
7
14
4
0
16
8
r =
3
>> [A,r] = matale(20,3)
A =
12
0
18
5
14
9
3
8
8
r =
3
>> A = matale(20,3)
A =
8
7
2
17
16
4
1
0
3
>>
Un point important concerne la gestion des variables entre le programme principal (ou le
workspace) et les fonctions de l'utilisateur. Toutes les variables dfinies l'intrieur d'une
fonction sont des variables locales cette fonction. La communication avec des variables du
programme principal (ou du workspace) ou avec des variables d'autres fonctions se fait
uniquement par les variables d'entre et sortie de la fonction. Une alternative existe toutefois:
il est possible de dclarer certaines variables comme des variables globales . Une variable
globale peut tre partage entre un programme principal et plusieurs fonctions sans qu'il soit
besoin de la spcifier parmi les variables d'entre-sortie des diffrentes fonctions. On dclare
une variable globale grce au mot cl global. Par exemple pour dclarer la variable numex
globale on crit global numex. Attention, la dclaration global numex doit tre reprise
dans chaque fonction utilisant numex comme variable.
: gal (x == y)
>
<
>=
<=
~ =
: diffrent de (x ~ = y)
&
et (x & y)
ou (x | y)
non (~ x)
Les oprateurs de comparaison et les oprateurs logiques sont utiliss essentiellement dans les
instructions de contrle, voir le paragraphe 5.3.
Instructions de contrle
Les instructions de contrle sous MATLAB sont trs proches de celles existant dans d'autres
langages de programmation.
Syntaxe :
forindice=borne_inf:borne_sup
squence d'instructions
end
o
indice
Voici un exemple d'utilisation d'une boucle pour calculer n! (le lecteur attentif sait calculer n!
plus simplement ... par exemple en excutant prod([1:n])).
>> n = 4;
>> nfac = 1;
>> for k = 1:n
nfac = nfac*k;
end
>> nfac
nfac =
24
>>
expression logique est une expression dont le rsultat peut tre vrai ou faux;
squence d'instructions est le traitement effectuer tant que expression logique est
vraie.
Interprtation :
Tant que expression logique est vraie le traitement squence d'instructionsest excut sous
forme d'une boucle. Lorsque expression logique devient faux, on passe l'instruction qui suit
immdiatement l'instruction de fin de boucle (end).
Remarque :
expression logique est en gnral le rsultat d'un test (par exemple i < Imax) ou le rsultat
d'une fonction logique (par exemple all(x)). Il est impratif que le traitement de la
squence d'instructions agisse sur le rsultat de expression logique sans quoi on boucle
indfiniment (-:.
Voici comment calculer n! avec une boucle while:
>> n = 4;
>> k = 1; nfac = 1;
>> while k <= n
nfac = nfac*k;
k = k+1;
end
>> nfac
nfac =
24
>>
L'instruction conditionne IF
On a parfois besoin d'excuter une squence d'instructions seulement dans le cas o une
condition donne est vrifie au pralable. Diffrentes formes d'instruction conditionne
existent sous MATLAB.
L'instruction conditionne la plus simple a la forme suivante:
Syntaxe :
ifexpression logique
squence d'instructions
end
o
expression logique est une expression dont le rsultat peut tre vrai ou faux;
Interprtation:
la squence d'instructions n'est excute que si le rsultat de l'valuation de l'expression
logique est vraie (c'est--dire vaut 1). Dans le cas contraire on excute l'instruction qui suit le
mot cl end. Dans le cas o l'expression logique est vraie, aprs excution de la squence
d'instructions on reprend le programme l'instruction qui suit le mot cl end.
Remarque :
Contrairement certains langages de programmation, il n'y a pas de mot cl << then >> dans
cette instruction conditionne. Notez galement que la marque de fin de bloc conditionn est
le mot cl end et non pas<< endif >>.
Il existe une squence conditionne sous forme d'alternatives:
Syntaxe :
ifexpression
logique
squence d'instructions 1
else
squence d'instructions 2
end
expression logique est une expression dont le rsultat peut tre vrai ou faux;
Interprtation :
Si expression logique est vraie la squence d'instructions 1 est excute, sinon c'est la
squence d'instructions 2 qui est excute. Le droulement du programme reprend ensuite la
premire instruction suivant le mot cl end.
Il est bien entendu possible d'imbriquer des squences d'instructions conditionnes (au sens o
la squence d'instruction conditionne contient des squences d'instructions conditionne).
Pour une meilleure lisibilit, il est recommand d'utiliser des indentations afin de mettre en
vidence l'imbrication des squences d'instructions conditionnes.
Il est possible d'effectuer un choix en cascade:
Syntaxe :
ifexpression
logique 1
squence d'instructions 1
elseif
expression logique 2
squence d'instructions 2
...
elseif
expression logique N
squence d'instructions N
else
Interprtation :
Si expression logique 1 est vraie la squence d'instructions 1 est excute et le programme
reprend ensuite la premire instruction suivant le mot cl end, sinon si expression logique 2
est vraie la squence d'instructions 2 est excute et le programme reprend ensuite la
premire instruction suivant le mot cl end, etc. Si aucune des expressions logiques 1 N
n'est vraie alors squence d'instructions par dfaut est excute.
Remarque :
Attention ne pas laisser d'espace entre else et if; le mot cl est elseif.
On utilise frquemment un choix en cascade lors d'initialisation de donnes. Par exemple, on
initialise une matrice A en fonction de la valeur d'une variable numex (numro d'exemple) de
la manire suivante:
if numex == 1
A = ones(n);
elseif numex == 2
A = magic(n);
elseif numex == 3 | numex == 4
A = rand(n);
else
error('numero d''exemple non prevu ...');
end
squence d'instructions N
otherwise
squence d'instructions par dfaut
end
o
var
cst1,
Interprtation :
Si la variable var est gale l'une des constantes cst1, ..., cstN, (par exemple csti) alors la
squence d'instructions correspondante (ici squence d'instructions i) est excute. Le
programme reprend ensuite la premire instruction suivant le mot-cl end. Si la variable var
n'est gale aucune des constantes la squence d'instructions par dfaut est excute.
Remarque :
La variable var doit bien entendu tre du mme type que les constantes cst1, ..., cstN.
Il n'est pas ncessaire de prvoir un cas par dfaut (bien que cela soit prfrable). S'il n'y a pas
de cas par dfaut et si la variable var n'est gale aucune des constantes, alors le programme
continue la premire instruction suivant le mot-cl end.
Il est possible de regrouper plusieurs << cas >> si la squence d'instructions excuter est la
mme pour ces diffrents cas. La syntaxe est alors,
case
Reprenons l'exemple o l'on souhaite initialiser une matrice A en fonction de la valeur prise
par une variable numrique numex (numro d'exemple). En utilisant un choix ventil on
obtient:
function
A = initA(n,numex)
switch numex
case 1,
A = ones(n)
case 2,
A = magic(n);
case {3,4},
A = rand(n);
otherwise
error('numero d''exemple non prevu ...');
end
Voici un exemple de choix ventil portant sur une variable de type chane de caractres.
rep = input('Votre reponse (oui, non, chepas) :');
switch rep
case {'oui','o'},
disp('bravo ...');
case {'non','n'}
disp('perdu ...');
case 'chepas'
disp('c''est pourtant facile ...');
end
L'excution normale
reprend ds que l'utilisateur enfonce une touche du clavier. L'instruction pause(n) suspend
l'excution du programme pendant n secondes.
Un exemple complet
Une technique de construction de carrs magiques d'ordre impair a t propose par Manuel
Moschopoulos au dbut du XIV sicle. Cette technique est dcrite dans [Histoire
d'Algorithmes, du caillou la puce, J.L. Chabert diteur, Belin 1994].
Notons l(x) le numro de la ligne et c(x) le numro de la colonne du carr sur lequel se trouve
l'entier x. Partant d'un carr d'ordre impair n=2k+1, la technique de Moschopoulos peut se
formuler comme suit:
Connaissant la position (l(x), c(x)) de l'entier x, on place l'entier x+1 suivant les rgles
suivantes:
si x n'est pas un multiple de n, alors
l(x+1) = 1 + l(x) modulo(n)
c(x+1) = 1 + c(x) modulo(n)
si x est un multiple de n, alors
l(x+1) = 2 + l(x) modulo(n)
c(x+1) = c(x) modulo(n)
Dans ces rgles pour la prise du modulo, le systme de rsidus que l'on considre est 1, 2, ...,
n et non pas 0, 1, ..., n-1.
La fonction magik met en oeuvre la mthode de Moschopoulos.
function M = magik(n)
%
% Calcule le carre magique d'ordre n selon la methode
% de Moschopoulous.
%
% Entree:
% n : ordre du carre (entier impair)
% Sortie:
% M : le carre magique
%
if rem(n,2) == 0,
msg = ['la methode de Moschopoulous ne construit que des carres' ...
,' d''ordre impair'];
error(msg)
end
k = (n-1)/2;
l(1) = k+2;
c(1) = k+1;
M(l(1),c(1)) = 1;
for x = 2:n.^2
[l(x),c(x)] = pos(x-1,l(x-1),c(x-1),n);
M(l(x),c(x)) = x;
% ou plus simplement M(pos(x,l(x-1),c(x-1))) = x;
end
La fonction utilise la fonction pos. Cette dernire fonction peut soit tre crite la suite de la
fonction magik si l'on dispose de la version 5 de MATLAB (dans ce cas il s'agira d'une sous-
fonction qui ne sera visible que de la fonction magik) soit tre sauvegarde dans un fichier
pos.m.
function [ly,cy] = pos(x,lx,cx,n)
%
% Retourne la position (indice de ligne ly et indice de colonne cy)
% dans le carre magique d'ordre n de l'entier y = x+1 selon la
% regle de Moschopoulous.
%
% Entree:
% n : ordre du carre (entier impair)
% x : l'entier considere
% lx : indice de ligne de l'entier x dans le carre magique
% cx : indice de colonne de l'entier x dans le carre magique
%
% Sortie:
% ly : indice de ligne de l'entier y=x+1 dans le carre magique
% cy : indice de colonne de l'entier y=x+1 dans le carre magique
%
if rem(x,n) == 0
ly = modulo(2+lx,n);
cy = modulo(cx,n);
else
ly = modulo(1+lx,n);
cy = modulo(1+cx,n);
end
Voici quelques exemples d'utilisation de la fonction magik. On vrifie que la somme des
lments des diffrentes lignes ainsi que la somme des lments des diffrentes colonnes sont
bien constantes. Pour calculer la somme des lments diagonaux c'est un peu plus compliqu.
On remarque que le carr magique construit diffre du carr magique retourn par la fonction
MATLAB incorpore magic.
>> magik(4)
??? Error using ==> magik
la methode de Moschopoulous
>> magik(5)
ans =
11
24
7
20
4
12
25
8
17
5
13
21
10
18
1
14
23
6
19
2
>> sum(magik(5),1)
ans =
65
65
65
65
>> sum(magik(5),2)
ans =
65
65
65
65
65
>> magic(5)
ans =
17
24
1
8
23
5
7
14
4
6
13
20
15
16
22
10
11
12
18
19
25
21
2
3
9