Nous allons voir ligne par ligne comment se fabriquer un traducteur d'anglais - français, français - anglais évolutif (évolutif dans le sens que plus on l'utilisera plus il sera complet). Je l'ai appelé Tafed (Traducteur Anglais Français EDitable)
Voyons voir sur Windows ou sur Linux ce qu'il nous faut
:
1) D'abord il faut que Perl soit installé
(sur Linux c'est déjà fait) sinon installer Perl.
2) Il nous faut aussi un dico_a-f.dico
: On va le créer dans la foulée
Pour Windows un clic droit de la souris sur le bureau,
puis Nouveau, puis document texte, OK
On ouvre ce document puis on écris dedans une
ou deux ligne, comme ci-dessous sans espace :
first,premier
link,lien
load,charger,télécharger,attrape,comprendre
last,dernier,final|last time=la dernière
fois
Voilà, le dico est fait, tout au moins il existe, on sauve en lui donnant le nom de " dico_a-f.dico ".
Il va vous accueillir et vous demander ce que vous voulez faire dans un petit menu, style :
**********************************************
Bonjour, ceci est le petit traducteur
Tafed
(Traducteur
Anglais
Français
EDitable)
Faite votre choix :
Anglais-français [1], Français-Anglais
[2], ajouter quelques définition [3], quitter [q ]
**********************************************
Puis suivant votre réponse il ouvrira le dico et
vous demandera d'entrer un mot ou une lettre
Puis il vérifiera les équivalences et vous
présentera le résultat comme ceci :
Si vous tapez last :
>last = dernier final (exemple. :
last time = la dernière fois)
si vous tapez juste ‘l’ :
>last = dernier final
>link = lien
>load = charger télécharger
attraper comprendre
Ceci est très pratique lorsqu'on ne se rappelle pas exactement de l'orthographe du mot.
Dans le cas ou vous choisissez d'éditer quelques
mots supplémentaires, il vous dira comment les entrer, puis vérifiera
si elle n'existe pas déjà dans le dico et vous demandera
de confirmer après vous avoir monter l'équivalence qu'il
à découverte comme ceci :
>Le mot link existe déjà
dans le dico, sous cette forme : link = lien
voulez vous le garder [Oui-Non] ?
Quand au Français-Anglais il va chercher dans toutes les traductions, sur tous les niveau, la concordance.
Maintenant nous allons voir comment on va lui faire faire
cela. Ligne par ligne mot par mot.
_________________________________________________________________
Code couleur
de cet exemple:
Chaque ligne
d'explication sera écrite
en grisé
Tous les numéro
de ligne de code seront
en Orangé
Tous les exemple
de sortie écran seront
en violé
Et toute les
10 lignes je récapitulerai en réécrivant l'ensemble
des 10 lignes sans commentaires. Si quelque chose vous échappe ou
vous laisse perplexe mailez
moi.
__________________________________________________________________________
Tout programme ou script Perl commence par un Bang. C'est une ligne qui va être reconnu par l'interpréteur du système que l'on utilise (MSDOS pour Windows, bash, ash, sh pour Linux).
Pour Linux il sera ainsi
:
01 #!/usr/bin/perl –w
alors que pour Windows il
sera comme ça:
01 #!perl –w
info :le petit " w " comme argument
signifie que vous désirez voir écrit le compte rendu de l'interprétation
du script passé au debuggage (très utile, il vous indique
les erreur et la ligne ou l'erreur à était relevé).
récapitulation
la ligne 01 s'appelle le Bang, qui indique que ce script doit être
interprété en Perl et commence par #!
puis le nom de l'interpréteur
("perl" sous windows) et ("/usr/bin/perl sous Linux), l'argument -w signifie
"tenez moi au courant des erreurs"
02 #
***************************************************************************
la ligne 02
est en commentaire, une ligne pour faire joli, toute les lignes commençant
par un dièse "#" son des commentaire au script. C'est à dire
qu'elle ne seront pas interprétées lorsque nous exécuterons
le script. (pareil que REM en DOS)
03 #
remd:
petit logiciel de traduction de mot simple anglais->français
04 #
et vice versa ainsi qu'une option Edit pour étoffer le dico.
05 #
pensez à faire suivre le dico_af-fr.dico dans le même répertoire.
06 #
alain adelmar 10 Août 2001. Version 1.02
les lignes
3,4 et 5 sont en commentaires et ne sont là que pour prévenir
le programmeur qui voudrai savoir comment est écrit ce script. Je
met toujours une balise remd: en seconde ligne (pour plus de précision
voir quoi.html et alias.html)
cela me permet de me faire un idée. En tapant "quoi tafed" il me
sort:
remd: petit logiciel de traduction de mot simple anglais->français
et vice versa ainsi qu'une option Edit pour étoffer le dico.
pensez à faire suivre le dico_uk-fr dans le même répertoire.
alain adelmar 10 Août 2001. Version 1.02
07
$dico = "dico_uk-fr";
la ligne 7
est une assignation*
c'est à
dire que l'on alloue une valeur (ici le nom du dico) à une variable
scalaire* ($dico)
c'est à
dire que la variable $dico aura comme valeur la suite de caractères
"dico_uk-fr"
c'est à
dire que l'on va prévenir le programme que quand il verra $dico
c'est le nom du dico
08 #
$kk = 0;
la ligne 8
ne sert à rien, car en commentaire, mais cette assignation de la
valeur 0 à la variable $kk est une initialisation
c'est à
dire que l'on alloue la valeur 0 à $kk pour pouvoir s'en servir
plus tard. Bien que perl est capable de géré les variables
en leur assignant une valeur nulle si elle n'on pas encore servie, il peut
être intéressant de savoir initialiser quelques variables.
Quand il y en a plusieurs on écrit:
$a = $b = $c
=0; # qui signifie que $a est égale a $b et a $c est
vaut 0.
On continu,
donc avec l'ouverture du fichier dico_uk-fr:
09 #
lecture du dico******************************************
la ligne 09
est un commentaire qui sert à prévenir le programmeur des
phases du script, ici il indique que l'on va lire le dico.
10
open F, "$dico" or die "Ouverture de dico impossible $!";
la ligne 10
représente l'ouverture en lecture, d'un fichier. La fonctionopen*
suivie de son Filehandle*(F)
que l'on va faire pointer, lier à "$dico" qui lui même contient
le nom du fichier, sers à ouvrir ce fichier (ici simplement en lecture).
+ d'info sur open et F.
Si l'ouverture
du fichier ne peut pas se faire correctement, soit parce qu'il est déjà
ouvert ou parce qu'il est inexistant ou son orthographe est inexacte, qu'il
à changé de place, enfin ....peut importe il faut arrêter
le script et prévenir l'utilisateur de pourquoi le script s'est
arrêté. Nous faisons tout ça grâce au deux fonctionsoret
die suivies d'une
ligne d'explication.
11
@traduction = <F>;
la ligne 11
est aussi une assignation car elle créée à la variable
liste @traduction en lui attribuant la valeur du contenu de dico_uk-fr,
représenté par le handle de fichier F. On peut traduire cette
ligne par:
- attribu la
totalité du fichier dico_uk-fr qui est représenté
par F à la variable liste @traduction (un élément
par ligne, c'est à dire que chaque ligne du fichier $dico sera un
élément de la liste @traduction ).
- créé
et prend en compte la variable liste @traduction comme étant le
contenu (ligne par ligne) du fichier représenté par le handle
de fichier <F> ($dico = "dico_uk-fr")
Personnellement
je me représente les pointes à gateaux comme "tout le contenu
de", comme "tout ce qui arrive de".
Bon récapitulons:
on a ouvert
le fichier dico_uk-fr représenté par F
on a placer
son contenu dans une variable liste qu'on a appelé @traduction
Il n'y a plus
qu'à fermer le fichier. Puissqu'on a son contenu plus besoin de
garder ce fichier ouvert.
12 close
F || die "fermeture impossible $!";
la ligne 12
ferme le fichier représenté par F (le handle de fichier)
de la même manière qu'il l'a ouverte mais avec la fonction
close. On aurai pu écrire comme à l'ouverture:
close F, "$dico" or die "fermeture de $dico impossible $!";
mais quand
on ferme il n'ai pas nessessaire de répéter l'assignation
du handle puissque Perl sait déjà que F représente
"$dico" et les deux barres ||
represente le même ou que or.
Souvent on a tendance à écrire juste:
close F
Mais il ne
coute rien de contrôler le retour de close et traiter l'erreur si
elle à lieu.
Maintenant
on va présenter le traducuteur et son menu
13
$x = "x*" x 25;
la ligne 13
est une concaténation*
c'est à
dire que la valeur de la variable $x sera calculé et sera le résultat
de la chaîne de caractère "x*" multiplier par 25
c'est à
dire 25 fois "x*" soit "x*x*x*x*x*x*x*x*x*x*x*x*x*x*x*x*x*x*x*x*x*x*x*x*x*"
Un expression
qui doit être calculé et mis en forme est une concaténation,
c'est le résultat de 25 reproduction de "x*".
14 $donc
= "\n\tdonc\n";
la ligne 14
est aussi une concaténation, une assignation à calculer.
Qui signifie que la variable $donc représente le signe
"\n" (un saut
de ligne, retour chariot) + le signe "\t" (une tabulation) a la suite,
suivie du mot "donc + le signe "\n" (un autre saut de ligne retour chariot).
Le tout est la valeur de $donc et donne:
donc
si nous avions
$y = "$x$donc$x"; # nous aurions en sortie:
x*x*x*x*x*x*x*x*x*x*x*x*x*x*x*x*x*x*x*x*x*x*x*x*x*
donc
x*x*x*x*x*x*x*x*x*x*x*x*x*x*x*x*x*x*x*x*x*x*x*x*x*
15 print
"\n\n\n$x\n";
la ligne 14
est une concaténation
de plusieurs signes précédés de la fonction print.
La fonction
print
donne l'ordre d'écrire sur le STDOUT (dans ce cas l'écran,
sur la console de l'application où vous avez ouvert le script ).
D'abord le signe "\n" qui est un saut de ligne retour chariot suivi de
deux autres puis la valeur $x puis un autre saut de ligne retour chariot.
résultat:
3 saut de ligne retour chariots + la valeur de $x + un autre saut de ligne
retour chariot. Ça donne
x*x*x*x*x*x*x*x*x*x*x*x*x*x*x*x*x*x*x*x*x*x*x*x*x*x*
16 MENU:print
"\nBienvenu sur le petit traducteur tafed\noffert par a_l_a_i_n \/\/ a_d_e_l_m_a_r
aadelmar\@free.fr\n";
17 print
"Anglais-français(1)\nFrançais-anlais(2)\nAjouter quelques
lignes au dico(3)\t\t\treponse: ";
la ligne 16
et 17 contiennent beaucoup de chose voyons cela mot à mot:
d'abord "MENU:"
qui est une balise qui servira pour revenir à cet endroit précisément
plus tard dans le programme.
Puis la fonction
print qui affichera à l'écran, un retour a la ligne suivi
de "Bienvenu sur le petit traducteur taf" saut de ligne, retour chariot
"offert par a_l_a_i_n" puis la barre "\" qui signifie (ne prendre en compte
le signe suivant que pour son aspect littéral, c'est à dire
qu'un \\n ne voudra pas dire saut de ligne mais juste les deux caractères
\n, car l'anti-slash devant signifie que le signe qui suit, n'a pas d'autre
signification que "une barre en travers" et un "n". Idem pour l'anti-slash
devant l'arobas "@" qui n'est pas une référence à
une variable liste mais simplement un arobas. Ceci est très
important : il faut toujours lire les signes de gauche à droite
en désamorçant avec les anti-slash ce qui doit être
désamorcé.
la ligne 17
elle commence par une fonction print donc continu d'écrire sur STDOUT,
la sortie standard (l'écran), par défaut.
Oui print
affiche sa sortie sur STDOUT lorsqu'il n'est
pas suivi d'un handle de fichier (une ou plusieurs lettre majuscules).
Nous verrons
plus loin comment écrire sur un fichier (ligne ).
récapitulation
des deux dernière lignes 16 et 17: (ça donnera):
Bienvenue
sur le petit traducteur tafed
offert par
a_l_a_i_n // a_d_e_l_m_a_r aadelmar@free.fr
Anglais-français(1)
Français-anlais(2)
Ajouter quelques
lignes au dico(3) reponse:
Voilà
ce que ça donne. C'est un menu, l'utilisateur prend connaissance
des choix qui lui sont fait et va donner le sien en entrant un caractère
suivi de la touche de validation <Enter>.
Donc on va
s'attendre à requeillir la réponse de l'utilisateur, et se
sur le clavier (il a que ça pour s'éxprimer dans cet exemple).
18 $trad
= <STDIN>;
la ligne 18
assigne à la variable $trad la valeur que l'utilisateur lui donnera.
C'est à
dire que <STDIN> (l'entré standard, le clavier) donnera la valeur
de $trad. Tant que vous n'aurez pas entrée un mot ou une ligne le
programme sera stoppé car il attend la touche "\n" (Enter) pour
valider l'entrée et du même coup la valeur de $trad.
C'est ainsi
que l'on questionne l'utilisateur en général . Important
donc.
19 chomp
$trad;
la ligne 19
va traiter la variable $trad (qui est ce que vous avez entré au
clavier + la touche <Enter> (pour valider)) par la fonction chomp
qui justement sert à ôter le
dernier caractère de la variable si
et seulement si ce caractère et un "\n"
(saut de ligne retour chariot, c'est à dire la touche
Enter qui justement sert à sauter une
ligne et à renvoyer le chariot au début de l'autre). Et oui,
lorsque vous appuyer sur Enter, vous valider une entrer mais aussi accessoirement
vous sauter une ligne et repositionner le chariot sur le début de
la suivante. La fonction chomp ôte cette touche si elle est placer
en fin de variable. On peut aussi écrire les deux dernière
phrase en une seule en tapant:
chomp($trad
= <SDTIN>);
récapitulation avant de poursuivre plus
avant: voici les lignes que l'on à vu.
01 #!perl –w
02 #
*************************************************
03 #
remd:
petit logiciel de traduction de mot simple anglais->français
04 #
et vice versa ainsi qu'une option Edit pour étoffer le dico.
05 #
pensez à faire suivre le dico_af-fr.dico dans le même répertoire.
06 #
alain adelmar 10 Août 2001. Version 1.02
07 $dico
= "dico_uk-fr";
08 #
$kk = 0;
09 #
lecture du dico******************************************
10 open
F, "$dico" or die "Ouverture de dico impossible $!";
11 @traduction
= <F>;
12 close
F || die "fermeture impossible $!";
13 $x
= "x*" x 25;
14 $donc
= "\n\tdonc\n";
15 print
"\n\n\n$x\n";
16 MENU:print
"\nBienvenu sur le petit traducteur tafed\noffert par a_l_a_i_n \/\/ a_d_e_l_m_a_r
aadelmar\@free.fr\n";
17 print
"Anglais-français(1)\nFrançais-anlais(2)\nAjouter quelques
lignes au dico(3)\t\t\treponse: ";
18 $trad
= <STDIN>;
19 chomp
$trad;
Pour le moment
on a défini quelques variables tel que le nom du fichier dico_uk-fr
On l'a ouvert,
lu et stocké dans une variable liste @
ouvert le script
en donnant un petit topo sur ce qu'il fait ( en guise de commentaire )
On a indiquer
aussi au script ou ce trouver le dico (dans $dico)
puis on à
afficher le menu de façon à ce que l'utilisateur sache ou
appuyer pour avoir ce qu'il veut.
Nous avons
aussi récupéré sa réponse $trad que nous avons
nettoyé du dernier caractère qui est le "\n" (Enter)
Nous allons
voir maintenant comment ouvrir et lire dans le dico, placer son contenu
dans une variable liste.
faire comprendre
a l'utilisateur que l'on a compris que l'on est bien dans la section qu'il
désire.
# menu possible de l'application**************************
if ($trad <= 1) {
print "$donc---- Anglais-français ----\n\n";
$trad = "af";
&le_mot($mota);
&anglais_francais;
}
elsif ($trad == 2) {
print "$donc---- Français-anglais ----\n";
$trad = "fa";
&le_mot($mota);
&francais_anglais($trad);
}
elsif ($trad >= 3) {
print "$donc---- Ajout au Dico perso ----\n";
print "Les lignes que vous ajoutez à votre dico personnel\ndoivent être écritent:\nmot_anglais,mot_français1,mot_francais2,mot_français3|exemple_angl = en_français\n";
print "(ne laisser pas d'espace entre les mots, juste une virgule)\n";
print "on y va? (o/n)\t";
$trad = "ed";
chomp ($repon = <STDIN>);
&oui_non($repon);
&edition($trad);
}
print "\n$x\n";
print "tchao !!!\n$x\n";
sub anglais_francais {
while ($mota ne "q"){
foreach $ligne(@traduction) {
chomp($ligne);
# laisser comme ça car plus complet
if ($ligne =~ /^$mota/) {
($line, $exemple)= split(/\|/, $ligne);
($angl, $fr, $fr1, $fr2, $fr3) =split(/,/, $line);
print "$angl = $fr\t$fr1\n";
if ($fr2 ne "") {
print "$angl = $fr2\t$fr3\n";
}
if ($exemple ne "") {
print "exemple: $exemple\n";
}
}
}
&choix;
}
# print "tchao !!!\n";
}
sub francais_anglais($trad) {
while ($mota ne "q"){
foreach $ligne(@traduction) {
($line, $exemple)= split(/\|/, $ligne);
($angl, $fr, $fr1, $fr2, $fr3) =split(/,/, $line);
if ($fr =~ /^$mota/) {
print "$fr = $angl\n";
}
if ($fr1 =~ /^$mota/) {
print "$fr1 = $angl\n";
}
if ($fr2 =~ /^$mota/) {
print "$fr2 = $angl\n";
}
if ($fr3 =~ /^$mota/) {
print "$fr3 = $angl\n";
}
}
&choix;
}
# print "tchao !!!\n$x\n";
}
sub edition($trad) {
while(! oui_non($repon)) {
LABEL:print "\nEntrez votre ligne\n";
chomp ($ligne_in = <STDIN>);
($linei, $exemplei)= split(/\|/, $ligne_in);
($angli, $fri, $fr1i, $fr2i, $fr3i) =split(/,/, $linei);
foreach $ligne(@traduction) {
($line, $exemple)= split(/\|/, $ligne);
($angl, $fr, $fr1, $fr2, $fr3) =split(/,/, $line);
if ($angl eq $angli|| $fr eq $fri ) {
print "cette ligne présente des similitudes avec la ligne:\n";
print "$angl = $fr\t$fr1\t$fr2\t$fr3\t$exemple\n";
print "voulez vous quand même entrer votre ligne dans le dico?\n";
$resp = <STDIN>;
chomp $resp;
if ($resp =~ /^n/i) {
print "elle ne sera donc pas intégré à votre dico\n";
goto LABEL;
}
}
}
$ligne_in = "$ligne_in" . "\n";
push @traduction, $ligne_in;
print "on continu? (o/n):\t";
chomp($repon = <STDIN>);
}
open(D, ">$dico") or die "Ouverture de dico impossible $!";
print D @traduction;
close D or die "fermeture impossible $!";
print "Vos lignes ont été rajouté au dictionnaire de traduction $dico\n";
&choix;
}
sub choix {
print "---------- (q) quitte, (m) menu ou un autre mot:\n";
$mota= <STDIN>;
chomp $mota;
if ($mota eq "m") {
goto MENU;
}
}
sub le_mot($mota) {
print "entrer votre mot pour le traduire ou (m) menu ou (q) quitter)\n";
chomp ($mota = <STDIN>);
}
sub oui_non($repon) {
my ($repon) = @_;
$repon =~ tr/A-Z/a-z/;
if ($repon =~ /^o|y/) {
return 0;
}
elsif ($repon =~ /^n/) {
return 1;
}
else {
print "\a";
print "Veuillez repondre par Oui ou par non\n";
chomp ($repon = <STDIN>);
&oui_non($repon);
}
}
END;
variable scalaire:
une variable scalaire est une variable qui ne contient qu'une information,
qu'une valeur. Maintenant cette information, cette valeur peut être
faite de plusieurs caractères, mais le tout ne représente
qu'une information. On pourrai remplacer scalaire par singulière.
Elle est représenté toujours avec un signe $ qui la précéde.
exemple: $s = "sardine";
Dans Perl il y à 3 types de variables prisent en compte: les
variables scalaires, les variables listes (ou tableaux) et les variables
de hashage.
variable liste ou
tableau: une variable liste ou variable tableau est une variable qui
contient un liste d'élément, de valeur. Maintenant elle ne
peut contenir qu'une valeur (si la liste n'a qu'un élément).
Les variable liste appelé aussi variable tableau sont représentés
par le signe @ qui les précédent.
exemple: @s = ("s", "a", "r", "d", "i", "n", "e");
ou $s[0] représentera l'élément
"s"
$s[1] représentera
l'élément "a"
etc... jusqu'à
$#s[-1] qui représentera
le dernier élément "e".
variable de hashage: une variable de hashage
est une variable qui contient une paire d'élément sous la
forme "clé" et "valeur". Ce qui est très pratique.
Les clés et valeurs peuvent être de n'importe quelle nature.
Elle sont représentés par le signe % qui les précédent.
exemple: %s = ("poisson" => "sardine");
ou $s{"poisson"} = "sardine";
une assignation:
assigné est le fait de donner une valeur à une variable,
le fait de convenir que telle variable ou autre bout de code contiendra
une valeur.
exemple: $a = "bonjour";
# on assigne le mot bonjour, la valeur "bonjour"
à la variable $a
on peut le faire aussi avec une procédure, une routine, une
fonction, un filehandle etc...
exemple: while (! oui-non) { # qui veut dire tant que
la procédure oui-non sera fausse faite
sub oui-non {
if ($respond =~ /^o|y/) {
return 1;
}
else {
return 0;
}
}
la concaténation:
c'est le résultat d'une mise en forme calculé. exemple:
print "\nBonjour\n" . "\tle
monde\n";
qui donnera une fois interprété, puis ajouté bout
à bout:
Bonjour
le monde
On dit de deux chaînes ou fichiers ajouter l'un à l'autre qu'ils sont concaténés. Pour savoir plus.
filehandle (poignée
à fichier, qui sers à attraper un fichier). Un filehandle
est la représentation d'une source de donnée, il est toujours
sous la forme d'une ou plusieurs lettres et/ou chiffre (ici F pour File,
mais on aurai pu l'appelé MYWAY). On se sers d'un filehandle pour
toute sortes de raisons, en fait chaque fois que l'on désigne une
source de données, comme:
Pour ouvrir un fichier, auquel cas on en profite pour lui assigner
sa valeur (l'endroit qu'il désigne, ici "$dico" qui représente
le fichier "dico_uk-fr" ):
open F, "$dico"
# que l'on aurez pu écrire aussi: open F, "dico_uk-fr" ou
aussi: open (F, "$dico") les 3 sont compris par Perl.
Pour désigner le contenu du fichier: @fichier = <F>; # se qui signifie que la variable liste @fichier a pour valeur tout le fichier, chaque ligne est un élément de la liste @fichier. Pratique non?
open (ouvre): la fonction
open suivie d'un filehandle de fichier ouvre un fichier. On l'écrit
comme ceci:
open
F, "$dico" or die
"Ouverture de $dico impossible $!";
ou open (F, "$dico")
||
die "Ouverture de $dico impossible$!";
Perl l'interprétera comme:
Ouvre
F, qui représente 'C:\doc\dico_uk-fr'
ou
arrête tout en affichant l'erreur "Ouverture
de C:\doc\dico_uk-fr impossible".
Si l'on avait voulu ouvrir le même
fichier mais en (lecture - écriture) on l'aurai indiqué en
ajoutant le signe > devant $dico comme:
open
F, ">$dico" or die
"Ouverture de $dico impossible $!";
auquel cas on pouvaient écrire
dedans.
On doit pensez aussi à prévoir
les problèmes d'ouvertures et fermetures de fichiers, donc on oriente
le <STDERR> vers la fermeture du script suivi d'un message explicatif
(ici "Ouverture de $dico impossible "). Pensez à refermer vos fichier,
sinon il reste ouvert pendant toute votre session, créant des problèmes
et même des bugs sous Windows.
or
ou||:
les fonctions or
et
||
représente le ou , si tel chose ne peut se faire les
instructions après ou sont exécutés.
die
(meurs): arrête le script, fini et vide les variables.
le menu c'est quoi?
C'est un éventail de propositions qui va permetre à l'utilisateur
d'orienter le programme suivant son choix, ce choix ce fera par le traitement
de la reponse de l'utilisateur. En général le menu est traité
dans une même procédure