Erlang – exemple 02
Cet exemple montre comment il est possible d'écrire des modules contenant
des fonctions puis de les invoquer dans la console interactive d'Erlang.
Remarques |
Code |
L'exemple à droite montre le code d'un petit module de démonstration
nommé demo.erl (l'extension
.erl est celle privilégiée pour les sources Erlang).
À noter :
- L'expression -module(demo). se termine
par un « . » comme
toutes les instructions Erlang,
et décrit le nom du module demo.erl (soyez
conformes!)
- L'expression -export(...) liste les
fonctions exportées de ce module. Elles seules pourront être invoquées
par le code client (celles qui ne sont pas exportées ne peuvent être
utilisées qu'à l'interne)
- Les fonctions sont identifiées par leur nom et par leur arité
(le nombre de paramètres qui doit leur être fourni). Il
est possible d'avoir plusieurs fonctions de même nom mais d'arité
différente. Ainsi, doubler/1 est
une fonction nommée doubler et ne
prenant qu'un paramètre, alors que multiplier/2
se nomme multiplier et prend deux paramètres
- Une fonction peut en appeler une autre, évidemment (voir
carre/1 qui invoque multiplier/2 dans ce code-ci)
- L'expression d'une fonction est son nom, ses paramètres entre
parenthèses, une flèche (->)
et le code qui lui est associé, le tout se terminant évidemment
par un « . »
|
-module(demo).
-export(
[doubler/1, multiplier/2,
carre/1,
coucou/0, coucou/1]).
doubler(X) ->
2 * X.
multiplier(X,Y) ->
X * Y.
carre(X) ->
multiplier(X, X).
coucou() ->
coucou('A qui de droit').
coucou(Nom) ->
io:format("Coucou, ~w ~n", [Nom]).
|
Notez l'écriture de coucou/0 et de
coucou/1. J'ai choisi d'exprimer coucou/0 comme
un appel à coucou/1 en passant le texte
'A qui de droit'. Notez les apostrophes autour du texte
passé en paramètre à coucou/1;
si j'avais utilisé les guillemets, l'affichage aurait présenté
une liste de valeurs
ASCII plutôt que du texte
formaté.
Concrètement, invoquer coucou/0 sous la
forme selon laquelle cette fonction est définie présentement affichera
Coucou, 'A qui de droit' alors que, si des guillemets
avaient été utilisés pour exprimer le paramètre
passé par coucou/0 à
coucou/1, l'affichage résultant aurait plutôt été
Coucou, [65,32,113,117,105,32,100,101,32,100,114,111,105,116].
La fonction io:format/2 est en fait la fonction
format/2 du module io. Elle utilise des codes
de formatage analogues à ceux de std::printf() en
C et
en C++,
mais privilégie les ~ plutôt que les
\ (ici, ~n signifie saut de ligne, alors
qu'en C
on aurait utilisé le caractère '\n').
Le second paramètre de io:format/2 est une
liste de valeurs à évaluer pour le texte à afficher.
Remarques |
Code |
L'exemple à droite montre quelques exemples d'invocation de fonctions
logées dans le module demo.erl ci-dessus :
- L'instruction c(demo). compile le module
demo.erl. Concrètement, le résultat de la compilation
d'un fichier .erl est un binaire Erlang
(extension .beam). Vous constaterez que
la compilation est une fonction et retourne un uplet (un tuple);
ici, parce que tout va bien, on obtient {ok,demo}
soit deux atomes, l'un indiquant que tout va bien et l'autre
représentant le module généré
- Quelques invocations de fonctions suivent, soit une de
coucou/0, une de carre/1 et une de
multiplier/2
|
Erlang R14B (erts-5.8.1.1) [smp:2:2] [rq:2] [async-threads:0]
Eshell V5.8.1.1 (abort with ^G)
1> c(demo).
{ok,demo}
2> demo:coucou().
Coucou, 'A qui de droit'
ok
3> demo:carre(5).
25
4> demo:multiplier(1234,5678).
7006652
5> demo:coucou(patrice).
Coucou, patrice
ok
6> demo:coucou(Patrice).
* 1: variable 'Patrice' is unbound
7> demo:coucou('Patrice').
Coucou, 'Patrice'
ok
8> demo:coucou("Patrice").
Coucou, [80,97,116,114,105,99,101]
ok
9>
|
Notez ensuite les appels à coucou/1, placés
ici pour illustrer quelques nuances du langage :
- L'expression demo:coucou(patrice) affichera
Coucou, patrice puis ok du fait que
la valeur d'un uplet est son nom, à tout le moins pour les fins de l'affichage
- L'expression demo:coucou(Patrice) provoquera
une erreur puisque Patrice est une variable et
qu'à ce stade, cette variable n'est pas encore associée à
un Pattern particulier
- L'expression demo:coucou('Patrice') affichera
Coucou, 'Patrice' puis ok tel qu'attendu;
alors que
- L'expression demo:coucou("Patrice") affichera
Coucou, [80,97,...,101] puis ok du
fait "Patrice" sera évalué comme une liste de
caractères sur huit bits
Quelques concepts :
- Les variables locales aux fonctions sont bel et bien locales, donc deux
fonctions peuvent utiliser un même nom de variable sans que cela n'entraîne de
conflits
- Il est clair qu'Erlang
n'est pas un langage fortement typé
- En retour, il est visible aussi que ce langage se prête à des
manipulations sur des structures binaires. Nous y reviendrons