On va commencer avec le classique programme hello world !.
#! /usr/local/bin/perl print "hello world !\n"; print "hello ", "world !\n"; print("hello ", "world !\n"); print "hello " . "world !\n";
On voit ici quatre lignes qui produisent exactement le même résultat. La première ligne est immédiatement compréhensible. La seconde illustre le fait que la fonction print prend une liste en argument. Les parenthèses autour de la liste sont optionnelles lorsqu'il n'y a pas d'ambiguïté. On peut cependant sans problème l'écrire avec des parenthèses, comme dans la troisième ligne.
La dernière ligne utilise un nouvel opérateur, ., qui effectue la concaténation de deux chaînes de caractères. Le résultat de cette concaténation est ensuite affiché par print.
Voila un programme d'exemple qui demande d'entrer un nom et met le résultat de cette demande dans une variable :
print "Entrez votre nom : "; $nom = <STDIN>; chomp($nom); print "Hello $nom\n";
La partie intéressante se situe au niveau des lignes 2 et 3.
La ligne 2 affecte à la variable $
nom le résultat de l'opérateur <>
appliqué au descripteur de fichier
STDIN.
L'opérateur de fichier <>
est utilisé pour lire une ou
plusieurs lignes d'un fichier. Dans un contexte scalaire comme ici, il
lira les données jusqu'au prochain retour-chariot, qui sera
d'ailleurs inclus dans le résultat.
Dans un contexte de tableau par contre, par exemple @lignes =
<
STDIN>
, l'opérateur renvoie l'ensemble des lignes
du fichier dans un tableau, ce qui peut produire des résultats
indésirables, si par exemple on applique cette ligne à un fichier
de plusieurs mégaoctets. Mais cette forme reste très utile pour
lire rapidement en mémoire le contenu entier d'un fichier.
La fonction chomp4.1 que l'on applique ensuite à la variable supprime le dernier caractère si c'est un newline. On peut d'ailleurs l'appliquer également à un tableau. Dans ce cas, elle enlèvera les newline à chaque élément du tableau.
On peut condenser ces deux lignes sous la forme
chomp($nom = <STDIN>);
La commande open permet d'ouvrir un fichier. Sa syntaxe est la suivante :
open(FILEHANDLE, EXPR);
En cas de succès, cette fonction renvoie une valeur non nulle, ce qui explique que l'on rencontre tout le temps la ligne
open(FILE, "fichier") or die "Cannot open fichier: $!";
La fonction die affiche sur STDERR la chaîne (ou la liste) passéee en argument, puis termine le script en renvoyant un code d'erreur non nul.
Le nom du filehandle doit être en majuscules (en fait, il ne s'agit que d'une convention, mais tout le monde la respecte). Quelques filehandles par défaut existent: STDIN, STDOUT, STDERR.
L'expression EXPR est le nom du fichier à ouvrir, précédé éventuellement d'un caractère qui précise le mode d'ouverture. Ces caractères sont résumés dans le tableau 4.1
|
Un nom de fichier particulier est à signaler : "-". Ouvrir
- est équivalent à ouvrir STDIN et ouvrir >-
revient à ouvrir STDOUT.
L'utilisation du caractère pipe |
permet d'envoyer du
texte sur l'entrée standard d'une commande, ou bien de récupérer
sa sortie standard (voir une illustration au
chapitre 12). Dans ce cas, la valeur retournée par
open est le numéro de processus (pid) du processus
lancé.
Pour lire sur un descripteur de fichier précédemment ouvert, on
utilise principalement l'opérateur
<>
, comme par exemple dans
$
nom = <STDIN>;, qui lit le filehandle précisé jusqu'au retour chariot suivant (qui est inclus dans le résultat).
Il existe également une commande read(FILEHANDLE,SCALAR,LENGTH) qui lit LENGTH octets de données dans la variable SCALAR depuis le fichier FILEHANDLE.
$len = read(FILE, $buffer, 512);
Cette commande est implémentée avec la fonction fread(). Pour effectuer un véritable appel-système à la fonction read(), il faut utiliser la commande sysread.
Pour lire un seul caractère, on peut utiliser la fonction getc(FILEHANDLE).
Le plus courant est l'utilisation de print auquel on fournit le descripteur de fichier en paramètre. Par exemple:
print FILE "hello world !\n";
Il faut noter qu'il n'y a pas de virgule entre le nom du descripteur de fichier et les éléments à écrire.
Il est possible d'accéder aux mêmes possibilités de formatage qu'en C en utilisant la fonction printf, à laquelle on passe les mêmes paramètres que son homologue en C :
printf STDOUT "Le nombre de %s est %3d.\n", $element, $nombre;
La fonction printf est cependant plus lente que la fonction print, que l'on utilisera donc de préférence.
De même que pour la lecture, il est possible d'effectuer un véritable appel-système à la fonction write() en utilisant syswrite(FILEHANDLE,SCALAR,LENGTH).
$len = syswrite(FILE, $buffer, length($buffer));
Elle est effectuée par la fonction close, à laquelle on fournit en paramètre le descripteur de fichier à fermer :
close(FILE);
Les opérations d'entrée-sortie sont bufferisées par défaut. Il
est possible de forcer perl à faire un flush après
chaque opération de lecture ou d'écriture en fixant la variable
spéciale $|
à une valeur non nulle, après avoir sélectionné le descripteur courant comme descripteur par défaut
grâce à la commande select.
On utilise communément cette syntaxe :
$oldfh = select(FILE); $| = 1; select($oldfh);
Note: la fonction select existe également sous la même forme qu'en C, pour effectuer l'appel-système select, ce qui peut induire une certaine confusion. Pour plus d'informations sur l'appel-système select, reportez-vous à la page de manuel de votre système :
$rin = $win = $ein = ''; vec($rin, fileno(STDIN), 1) = 1; vec($win, fileno(STDOUT), 1) = 1; $ein = $rin | $win; ($nfound, $timeleft) = select($rout = $rin, $wout = $win, $eout = $ein, $timeout);
Si on désire plus de lisibilité pour fixer le buffering, on peut utiliser le module FileHandle :
use FileHandle; autoflush FILE 1;