Académique Documents
Professionnel Documents
Culture Documents
Francis Sergeraert
Chapitre 1
Premires sessions Maple
1.1 propos du systme d'exploitation utilis.
Le logiciel Maple est utilisable sur tout poste de travail Windows, Mac ou
Unix, aprs une installation du logiciel, trs simple, surtout sous Windows et Mac.
Une fois le logiciel install, les procdures d'utilisation sont les mmes, des dtails
minimes prs, qui ne concernent jamais l'essentiel de ce qui est fait avec ce logiciel.
Les micro-dirences sont dues aux traditions plus ou moins bien dnies pour
chaque environnement, et aussi aux ressources disponibles dans chaque systme
d'exploitation. Pour ne pas alourdir inutilement la prsentation, on ne considrera
ici que le cas de Maple utilis sous Windows.
Pour rassurer le lecteur angoiss, examinons immdiatement une telle dirence
an d'en mettre en vidence la futilit1 . Frquemment l'utilisateur doit ouvrir une
nouvelle fentre, il faut dire une nouvelle feuille de travail (worksheet). L'utilisateur
Windows a trois mthodes quivalentes pour le faire :
1. Il peut cliquer sur le premier bouton de la barre d'outils, dont l'icne reprsente une feuille vierge corne en haut droite. La feuille vierge souhaite
s'ouvre aussitt.
lecteur dbutant complet n'est pas concern par le reste de cette section.
l'indication correspondante pour une version dirente, plus ancienne ou plus rcente.
C:\Program Files\Maple 6\BIN.WNT\wmaple.exe, berk !
4 Ce manuel a t prpar avec la Release 6 ; pendant sa prparation, la release 7 est parue ;
les dirences avec la release 6 sont, pour ce qui concerne notre sujet, ngligeables.
5 Ces dirences ne sont pas anodines ; sur beaucoup de questions la release 5 est beaucoup
plus commode que la release 4. En particulier la release 5 permet la programmation fonctionnelle,
.
outil capital pour beaucoup de questions, qu'on examinera en temps utile, voir
3 Probablement
2. Le bouton
servant agrandir la fentre en plein cran ou au contraire
la rduire en cran partiel ;
3. Le bouton
L'usage de ces boutons est banal et il n'y a pas lieu d'en parler. Si la fentre est
en cran partiel, sa taille et sa position peuvent tre modies par les procdures
habituelles.
Sous le bandeau titre, on trouve le bandeau des menus :
Conseil 1 Ne cliquez pas sur les boutons de la barre d'outils tant que vous
n'avez pas raisonnablement compris leur usage. Pour ce faire, faites en d'abord au
besoin l'exprience sparment dans une micro-session Maple ddie uniquement
cette question. Sinon, abstenez-vous prudemment.
6 <Return>
Il peut vous tre utile dans ce registre d'activer l'option Balloon Help du menu
Help ; si ceci a t fait, le passage du pointeur souris sur un bouton provoque
l'achage d'une bulle explicative sur la nature du bouton. On avait montr un
exemple page 1. Cette explication n'est pas toujours susante pour le dbutant.
Certains boutons ont deux positions ; l'une o (bouton en attente) indique que
l'option correspondante est pour le moment inactive, l'autre on (bouton pouss)
indique au contraire que l'option est active. Par exemple le mode Text est inactif
si le bouton
est o :
est on :
Le plus simple est alors d'utiliser, plusieurs fois au besoin, la touche Ctrl-Z
(Undo Typing) jusqu' revenir au mode standard. Autre solution, on balaie la
zone trange avec la souris en dbordant un peu sur la zone standard :
dans vos commandes Maple par le procd de tous les langages de programmation :
sur toute ligne de commande, le caractre #, sans changer de mode, indique
Maple que le texte qui le suit sur sa ligne est un commentaire. Ceci sut largement
pendant l'initiation.
Exemple de simple commentaire :
Il est important de bien comprendre dans un tel cas que les boutons Windows
de la feuille de travail sont achs sur la partie droite du bandeau des menus, juste
au-dessous des boutons analogues pour la fentre Maple entire, mthode gnrale
Windows trs commode l'usage mais qui surprend toujours les dbutants. On les
indique ici l'aide de notre che rouge :
Il peut alors dcider d'ouvrir une autre fentre avec la touche7 Ctrl-N :
7 Voir
Section 1.1.
On voit que la deuxime fentre est active (foreground) alors que la premire est
passive (background) ; noter en particulier les couleurs des bandeaux des fentres
selon leur tat. On peut nanmoins prfrer voir simultanment les deux fentres ;
ceci est obtenu en demandant l'option Vertical du menu Window :
10
Un systme d'aide l'utilisateur, trs riche, trs bien conu, est accessible par
le menu Help. Par exemple, si on souhaite voir la documentation de base de la
procdure Maple prdnie solve, on demande l'option Topic Search du menu
Help :
11
On obtient :
Sur la reproduction donne ici, la fentre aide est minuscule et l'aide est en
dnitive invisible moins de faire passer cette fentre en mode plein cran, en
:
cliquant sur son bouton
12
puis en faisant glisser le bouton ascenseur, montr ci-dessus par la che rouge, on
peut atteindre la partie qui nous intresse :
13
et on retrouve bien notre fentre, qui est d'ailleurs passe aussi en mode plein
cran comme la fentre d'aide :
14
15
la conguration standard, les calculs eectus sur une feuille sont connus des autres
feuilles, et il ne s'agit donc pas d'un vrai paralllisme ; l'option -km p de la commande
systme lanant Maple demande au contraire que les direntes feuilles s'ignorent compltement
et plusieurs sessions direntes peuvent alors tre menes de front.
16
Conseil 3 Le plus souvent on peut s'organiser dans une session pour avoir une
seule feuille de travail principale, au plus une seule feuille de travail petite exprience, supprimer ds que la dite exprience est termine. Enn il est prfrable
de dtruire les feuilles d'aide ds que leur consultation est termine ; le cas chant
on peut les rouvrir trs facilement.
Windows, Maple peut aussi tre lanc en ouvrant un chier feuille de travail, dont le
code extension est normalement .mws ; le cas chant, la feuille en question est pralablement
installe dans la session ; voir cependant ce qui est expliqu Section 1.5.
17
En fait le crochet ouvrant [ n'est pas un caractre, c'est une sorte d'accolade
pour indiquer la porte d'un groupe d'excution (Execution Group), notion qu'il
est inutile de dtailler pour le moment ; vous verrez clairement de quoi il s'agit par
la suite. Dans les exemples cits dans ce manuel, nous ne montrerons pas, sauf cas
trs particuliers, ces indicateurs. Le seul prompt Maple est en fait le caractre >.
Comme premier exemple de travail Maple, supposons qu'on souhaite valuer
l'intgrale suivante :
Z
1+x
dx,
1 + x2 + x4
1
Il faut entrer :
..................................................................................................................................
..................................................................................................................................
Le texte entr est une expression Maple-Input, constitue d'une suite de caractres
ASCII, forme externe d'un objet Maple dont on s'apprte demander l'valuation.
Pour ce faire, aprs avoir entr le ; terminal, indispensable, on tape la touche
<Entre>. Il est important de comprendre ce point que cette touche <Entre>
n'est en aucune faon le caractre de passage la ligne suivante comme dans
presque tous les traitements de texte. Conventionnellement, sous Maple, cette
touche demande Maple l'valuation de tous les objets du groupe d'excution
o le curseur est positionn ; ici ce groupe est rduit la seule ligne dnissant
l'intgrale cherche. Une fois que cette touche <Entre> est. . . entre, Maple
value l'intgrale demande et ache le rsultat comme suit :
..................................................................................................................................
..................................................................................................................................
Les manuels grand public prfrent souvent montrer une copie bitmap de
la fentre obtenue :
18
On voit que c'est beaucoup plus encombrant et souvent nalement bien moins
prcis que ce qui est indiqu par une typographie standard simulant avec une bonne
approximation ce qui est observ dans la fentre Maple. On n'utilisera dsormais
une copie exacte d'une fentre Maple que dans des circonstances relativement
exceptionnelles.
On a donc obtenu le rsultat :
Z
1+x
5
1
dx =
3 ln 3,
2
4
1+x +x
36
4
1
dj pas si facile atteindre avec papier-crayon.
Trs souvent, comme la syntaxe requise pour entrer les expressions valuer est
relativement complexe et ne pardonne aucune imprcision, l'utilisateur Maple fait
des fautes de natures assez varies, demandant un minimum de lucidit, quelquefois
beaucoup, pour tre identies puis corriges. Supposons par exemple que nous
oublions dans l'entre de l'expression intgrale la premire parenthse fermante,
celle qui ferme le numrateur (1+x_ : Maple ache alors un message d'erreur en
petits caractres mauves, sur la ligne infrieure :
..................................................................................................................................
..................................................................................................................................
> |
..................................................................................................................................
Pas d'erreur dtecte, mais le rsultat n'est pas exactement celui qui est espr ! Vu
l'apparente correction du rsultat ( !), Maple a ouvert un nouveau groupe d'excution o il a positionn le curseur en attente de l'expression suivante valuer.
Notre intgrale semblait convergente, et pourtant Maple donne le rsultat ,
signiant au contraire qu'il l'a trouve divergente. Le mcanisme d'appel de procdure de Maple est trs puissant, mais de temps autre il implique que ce qui est
en fait une erreur d'entre russisse tre interprt d'une faon assez surprenante pour l'utilisateur non initi. Il se trouve qu'ici l'expression valuer, malgr
l'apparente faute de parenthsage, est tout--fait correcte pour Maple, sauf qu'il a
valu en fait :
Z
x
dx,
1+
1 + x2 + x4
1
19
qui est bien une intgrale divergente. Il n'est pas vraiment vident de comprendre
comment Maple a pu aboutir cette interprtation ; nous verrons ce point en temps
utile, voir page 115. On entre ici en debugging proprement dit. Il faut lucider
comment Maple a pu obtenir ce rsultat bien troublant. L'examen soigneux de
l'expression entre nit par faire comprendre que le numrateur 1+x de l'intgrande
n'est pas correctement parenths. On positionne le curseur derrire le x critique
par un clic de souris ou l'aide des touches directionnelles du clavier (,,
et ) et on ajoute la parenthse manquante ; on tape <Entre> et on obtient
ce rsultat :
..................................................................................................................................
..................................................................................................................................
..................................................................................................................................
Chaque fois qu'un rsultat est (ou, pour Maple, parat) correct, Maple ouvre
aprs l'achage du rsultat un groupe d'excution o il positionne le curseur. Si
un tel groupe tait dj prsent, Maple ne cre pas un nouveau groupe, mais il
positionne le curseur au dbut de la dernire ligne du groupe d'excution suivant
celui qui vient d'tre excut. On ne montrera plus dsormais ce groupe suivant
dans nos exemples.
Notre calcul d'intgrale est cette fois russi, au moins pour un mathmaticien.
Le rsultat exact obtenu, ncessitant pour tre exprim le radical, le nombre
et le logarithme, n'est pas forcment celui qui est souhait par exemple par le
physicien, quand il cherche un rsultat numrique. Notre physicien pourra alors
pour atteindre le but recherch excuter :
..................................................................................................................................
> evalf(%) ;
.4810966632
..................................................................................................................................
20
..................................................................................................................................
..................................................................................................................................
C'tait le but de cette session qu'il faut donc maintenant terminer, mais il est
peut-tre prfrable de la sauvegarder en vue d'une rutilisation ultrieure. Pour ce
faire on active l'option Save du menu File, ou encore on utilise le raccourci clacier
Ctrl-S ; une fentre de dialogue intitule Enregistrer sous s'ouvre, permettant
de prciser le chier de sauvegarde souhait. Il faut prendre son temps pour en
comprendre les possibilits.
Cinq mini-fentres sont incluses. La premire, une seule ligne o le curseur est
positionn, indique *.mws, ce texte apparaissant slectionn, c'est--dire surcharg
par une bande colore, bleue sous le standard Windows. La fentre juste infrieure
rappelle pour mmoire les chiers dj prsents dans le dossier en cours. A droite
de cette fentre se trouve justement une autre fentre qui indique la situation
actuelle par rapport l'ensemble des dossiers de l'unit de disque active. En haut,
les dossiers actifs sont ouverts. Ici le rpertoire en cours est donc :
D:\Program Files\Maple 6\Users\
C'est ce que vous trouverez10 la premire fois aprs installation de Maple. Il est
donc important de savoir comment grer cette situation. Il ne faut en aucune faon
sauvegarder son chier dans ce dossier considrer comme systme. La tradition
sous Windows consiste, en utilisant par exemple Windows-Explorer, crer dans le
dossier D:\Mes Documents\ un dossier Maple. Ceci fait, indpendamment de Maple,
il faut maintenant, dans Maple, remonter jusqu' C:\ en cliquant rapidement
deus fois dans la fentre de dialogue Maple sur cette indication ; on obtient quelque
chose comme :
10 L'installation
21
Puis il faut descendre pour atteindre notre dossier, donc cliquer d'abord
(deux fois) sur Mes Documents :
Le dossier Maple install, par exemple l'aide de Windows Explorer, sous le dossier
Mes Documents, peut tre slectionn par un clic de souris, ou par utilisation de la
touche directionnelle `', ou encore en entrant (deux fois) `m' au clavier :
22
Enn on clique sur OK, ou on tape simplement <Entre>. La fentre de dialogue disparat, mais notre belle feuille de travail est enregistre comme le chier :
D:\Mes Documents\Maple\Integral-1.mws
23
Warning 4 Dans la fentre Enregistrer sous, bien noter que le dossier actif
Ne changez rien la mini-fentre intitule Enregistrer au format : ; autrement dit considrez comme une norme sans exception que votre feuille de travail
est sauvegarde sous un nom de chier d'extension .mws, mnmonique de MapleWorkSheet.
Notez que quand votre feuille est sauvegarde, le nom choisi apparat dans
le bandeau titre de votre fentre Maple. D'une faon gnrale est ainsi dsigne
la feuille de travail actuellement active, [Untitled(x)] si c'est une feuille non
sauvegarde, le nombre x voluant au gr des crations de nouvelles feuilles de
travail. La liste des fentres actuellement existantes est disponible dans le menu
Windows, la fentre active tant marque X.
Vous pouvez alors, maintenant que votre feuille est sauvegarde, continuer votre
travail, entrer de nouvelles commandes, etc. Vous pouvez aussi fermer votre session
Maple, par exemple en cliquant sur le bouton Windows
en haut droite de la
fentre Maple.
Si vous tentez de terminer une session Maple et qu'une ou plusieurs fentres
ne sont pas sauvegardes, Maple vous demande de conrmer votre dcision pour
chaque fentre successivement. Prenez soin de rchir quelques secondes pour
viter de perdre un travail peut-tre prcieux.
24
..................................................................................................................................
> x := 34 ;
x := 34
> x + 3 ;
37
> |
..................................................................................................................................
Vous laissez le curseur l o il est positionn et vous sauvegardez cette feuille de travail ; vous terminez la session Maple et allez prendre un caf. Ceci fait, vous revenez
votre poste de travail, relancez une session Maple et ouvrez la feuille qui avait t
prcdemment sauvegarde. Le curseur est positionn toujours au dernier groupe
d'excution, pour le moment vide. Vous entrez au clavier x + 3 ;<Entre>.
Votre feuille de travail devient :
..................................................................................................................................
> x := 34 ;
x := 34
> x + 3 ;
37
> x + 3 ;
x+3
..................................................................................................................................
Dans la premire session, on avait aect au symbole x l'entier 34, puis on avait
valu l'objet x+3 ; on dtaillera bientt le fonctionnement de ces choses, mais il
est naturel de voir l 37 comme rsultat de l'valuation, compte tenu de la valeur
de x. La session est alors arrte aprs sauvegarde.
Ensuite on lance une autre session Maple ; on y ouvre la feuille de travail
sauvegarde la n de la session prcdente. On retrouve le curseur positionn
l o il tait au moment de la sauvegarde, mais ceci ne signie en aucune faon
que les instructions prcdentes ont t pralablement excutes. En particulier,
pour le symbole x, tout se passe comme si la valeur de la session prcdente, 34,
tait en fait perdue, et c'est pourquoi l'valuation de x+3 retourne seulement x+3 :
un symbole sans valeur a, sous Maple, lui-mme comme valeur, en fait valeur
par dfaut ; ce mcanisme est trs important en calcul symbolique et sera dtaill
plus loin. C'est pourquoi on a maintenant l'cran deux valuations apparemment
successives de x+3 avec des rsultats dirents.
Mais vous pouvez si vous le souhaitez faire rexcuter toute votre feuille. Activez l'option Execute Worksheet du menu Edit. Toute la feuille va tre rexcute et cette fois les deux valuations de x+3 donnent le rsultat 37, cause de
l'aectation pralable de 34 x. Autrement dit la feuille est inchange sauf que le
dernier rsultat est maintenant 37. Un corollaire est le conseil qui suit.
soient entirement rexcutables sans incident. Sinon elles peuvent rapidement devenir dicilement utilisables. Pour que ce travail de mise au propre ne soit pas trop
pnible, faites la mise jour ncessaire de temps autre pendant votre session.
L'option Execute Worksheet du menu Edit vous permet de vrier rapide25
ment l'tat de votre feuille de travail ce propos. Toutes les commandes Maple de
votre feuille sont alors excutes squentiellement. Mme si une commande termine
sur erreur, Maple continue et lance aussitt l'excution de la commande suivante,
jusqu' la n de la feuille. Le dlement est tellement rapide qu'une telle erreur
peut passer visuellement inaperue, et votre feuille n'est peut-tre pas alors dans
l'tat que vous souhaitez. Mais vous pouvez lancer la recherche arrire12 de toutes
les occurences de Error dans votre feuille pour conclure ce propos.
Maple 6 est la premire version de ce logiciel possdant un mcanisme de sauvegarde automatique, voir l'option Autosave du menu Options et la page de
documentation worksheet,options,autosave. Il arrive en eet de temps autre
qu'un calcul trop complexe, ou encore demand de faon errone, provoque un
crash complet de la session Maple ; dans un tel cas, tous les calculs prcdemment prpars peuvent tre perdus. L'option Autosave permet de demander
Maple la sauvegarde systmatique, intervalles rguliers, de votre feuille de travail, sous un nom de chier particulier construit partir du nom du chier associ
en ajoutant _MAS (Maple AutoSave). Les risques de grosses pertes sont ainsi trs
sensiblement diminus. Pour tout travail d'envergure, il faut absolument utiliser
cette possibilit.
26
3. Full Text Search : Trs utile dans les cas diciles ; vous proposez un mot et
Maple cherche toutes les occurences de ce mot dans les feuilles d'aide ; elles
sont de plus classes par la frquence d'apparition. Voir ci-dessous un usage
frquent.
Malgr le ct forcment publicitaire du New User's Tour, il ne doit pas tre
nglig. Aprs plusieurs annes d'utilisation de Maple, on a la surprise d'y trouver
encore de temps autre des tuyaux utiles !
Au passage, les pages proposes peuvent donner des ides pour des sujets plus
ou moins connexes ; ainsi quand on cherche la documentation pour la fonction ,
13 Il
27
Les branches voisines sont aussi aches, de sorte que l'exploration de cet arbre
permet quelquefois d'atteindre logiquement la feuille qui en fait tait approprie.
La manuvre usuelle de souris permet d'augmenter ou au contraire de diminuer
la hauteur de ce bandeau, et donc de s'adapter la situation du moment. Par
example, si vous cherchez eectuer une simplication visuellement possible dans
une expression rsultat complique, vous allez probablement tenter simplify, souvent sans succs. tout hasard vous explorez la page simplify sans rien y trouver
de nouveau par rapport ce que vous pensez connatre. En bout de course, pensez
alors explorer l'arborescence du systme d'aide. Pour ce faire examinez le bandeau o vous voyez que le chemin jusqu' simplify est :
14 Un
examen soigneux montre que ce n'est pas strictement parlant un arbre : il peut exister
plusieurs chemins de la racine vers une feuille, mais ce moteur de recherche n'en est que plus
intressant ;
28
..................................................................................................................................
Mathematics
Algebra
Expression Manipulation
Simplifying
Simplify
..................................................................................................................................
Explorant l'arbre, vous voyez qu'il y a beaucoup d'autres faons de simplier que
d'utiliser la procdure simplify ; par exemple les procdures normal, radnormal,
combine, qui souvent correspondent ce qui en fait est recherch. En dsespoir de
cause, on peut mme se demander si c'est vraiment une simplication qui est recherche. Au mme niveau de la hirarchie que Simplifying , on trouve par exemple
Factoring qui peut mener sur d'autres pistes. Cet outil de recherche ne doit jamais
tre nglig.
Une autre mthode peut encore tre exploite quand une feuille d'aide se rvle
inapproprie pour un problme particulier : la n de cette feuille ache frquemment un certain nombre de liens hypertextes vers des sujets voisins ; c'est souvent
de cette faon qu'on atteint enn la page cherche !
prcisment elles sont accessibles par un mcanisme assez lourd qui doit aussi citer le
nom du package.
29
dduisez qu'un package networks est disponible, contenant entre autres une procdure chrompoly, calculant trs probablement le polynme chromatique d'un graphe.
On sait que le nombre chromatique s'en dduit ; le package networks fournira tous
les outils ncessaires pour construire et manipuler les graphes ; le problme est
rsolu.
1.7.1
<Return> ou <Shift-Return> ?
..................................................................................................................................
Si vous ne connaissez pas la technique ad hoc, vous aurez les plus grandes
dicults imiter exactement ce qui est montr ci-dessus. La procdure SquareSum
16 Noter
qu'en Maple majuscules et minuscules sont distingues dans les symboles, comme en
C ou Java.
17 La rponse (ouput) Maple pour la procdure entre est en fait un peu plus vaste ; l'achage
simpli prvu ici est susant ; on procdera presque toujours de mme dans la suite.
31
est organise sur trois lignes, de sorte qu'aprs avoir entr la premire ligne, vous
allez, quoi de plus naturel, actionner la touche <Entre> pour taper la ligne
suivante. Vous voyez alors Maple vous compliquer la vie comme suit :
..................................................................................................................................
..................................................................................................................................
Maple est eectivement pass la ligne suivante, a mme insr en dbut de ligne
un autre signal de prompt (>) ; de plus, sous cette ligne, il fait gurer en petits
caractres bleus un Warning signalant une n prmature d'input. Vous pouvez
maintenant entrer la deuxime ligne RETURN(add(item2, item=list)), puis taper
nouveau <Entre> ; un troisime prompt s'ache et le Warning descend pour
tre maintenant en quatrime ligne. Vous entrez le end ; terminal et quand pour
la troisime fois vous tapez la touche <Entre>, le Warning disparat comme par
enchantement et vous obtenez ceci :
..................................................................................................................................
..................................................................................................................................
La seule dirence avec ce qui avait t montr au dbut comme solution de rfrence est la prsence de prompts au dbut de chaque ligne de texte source de la
procdure. Ce n'est pas franchement gnant, si bien que les utilisateurs dbutants
commencent en gnral par se contenter de cette faon de faire.
Pourtant, au fur et mesure que vous progresserez, vous crirez des procdures
de plus en plus longues ; pendant une mise au point, il arrive de temps autre qu'on
dcide de couper une instruction un peu longue sur une ligne de telle faon qu'elle
occupe deux lignes ou plus ; d'autres fois il faut insrer dans le texte de nouvelles
instructions devenues ncessaires, exprience faite. Considrons la procdure log2
ci-dessous, destine calculer le logarithme de base 2 d'un rel positif.
..................................................................................................................................
> log2(3) ;
1.584962501
> log2(-3) ;
1.584962501 + 4.532360143 I
..................................................................................................................................
Cette procdure est correcte, mais retourne comme il se doit un complexe si l'argument x est ngatif. Il peut se faire, dans un contexte donn, que cette circonstance
soit exclue, auquel cas le programmeur prfrera le cas chant interrompre immdiatement l'excution avec un message d'erreur clair. La solution suivante18 peut
18 Il
est plus simple de typer le paramtre, voir page 80, mais le message d'erreur peut ne pas
tre celui qui est souhait.
32
tre adopte :
..................................................................................................................................
..................................................................................................................................
Supposons donc que vous ayez d'abord entr la premire version, puis que vous
prfriez la deuxime. L'habitude des traitements de textes peut vous suggrer
pour la modication la solution suivante : positionner le curseur la n de la
premire ligne, puis entrer un retour chariot <Entre> pour intercaler la ligne
if x <= 0 ... ; vous pourrez le faire autant de fois que vous voulez, la disposition
reste absolument inchange ! ! De plus, chaque essai, la dnition de procdure
est value et le curseur va se positionner aprs le rsultat ach en bleu, au dbut
du groupe d'excution suivant.
Devant ce comportement trange de l'diteur Maple, vous allez probablement
tenter autre chose : positionner le curseur au dbut de la deuxime ligne, puis
entrer devant RETURN(... le dbut de l'instruction conditionnelle que vous voulez
insrer :
..................................................................................................................................
..................................................................................................................................
Ceci fait, vous tapez nouveau la touche <Entre> pour partager la longue ligne
en deux parties, esprant continuer de la mme faon sur la ligne suivante. Eh bien
non, la deuxime ligne refuse la sparation ! De plus le texte procdure est valu
dans son tat trs provisoire, incomprhensible pour Maple, d'o l'erreur :
..................................................................................................................................
..................................................................................................................................
aussi touche Maj (caractres majuscules) sur certains claviers, ou encore Shift
selon la terminologie anglaise.
33
de tout le groupe d'excution, quelle qu'en soit la taille. Ce n'est que trs
auxiliairement que Maple introduit un retour chariot la n du groupe
d'excution pour sparer l'entre (input) du groupe, en caractres tltypes
rouges, de la sortie (output), en petits caractres bleus. Cette touche n'introduit aucun retour chariot l o le curseur tait positionn.
2. La touche <-Entre> insre banalement un retour chariot l o le curseur est positionn, sans lancer quelque valuation que ce soit.
Ce choix des concepteurs de Maple est assez discutable, mais il est ainsi. En
consquence, quand une commande ncessite plusieurs lignes de texte, il est bien
meilleur de passer la ligne suivante l'aide de <-Entre>. Vous ne recevrez pas continuellement le Warning intempestif premature end of input, et vous
n'aurez logiquement qu'un seul prompt > au dbut de votre groupe d'excution. C'est seulement quand votre groupe d'excution sera entirement termin,
par exemple quand vous aurez entr le end ; terminal de votre procdure, c'est
seulement ce moment que vous taperez une touche <Entre> simple, sans ,
pour demander l'valuation. Ceci doit devenir rexe :
1. La touche <-Entre> pour le passage ordinaire la ligne suivante ;
2. la touche considrer comme spciale <Entre> pour la terminaison du
groupe et l'valuation.
Par ailleurs, les fautes de syntaxe dtectables seront dtectes exactement dans
les mmes conditions au moment de <Entre>, ce qui permet de mieux disjoindre
la phase d'criture du texte de celle de l'analyse syntaxique et correction.
34
..................................................................................................................................
..................................................................................................................................
..................................................................................................................................
une prcision encore meilleure. Le principe est simple : si pendant l'action des
touches de mouvement du curseur, quelles qu'elles soient, vous maintenez en plus
la touche enfonce, la zone parcourue par le curseur est slectionne. Par
exemple, si, cas assez frquent, vous voulez eacer toute la feuille partir d'un point
donn, vous avez un moyen trs simple pour le faire : vous positionnez le curseur
au point coupure, puis vous actionnez simultanment les trois touches <Ctrl-Fin> ; ce seul geste slectionne la zone voulue. Ensuite un coup de <Suppr> et
la suppression est faite. Notez aussi dans ce registre que si vous tes positionn
en dbut de groupe d'excution, juste aprs le prompt Maple (>), vous pouvez en
actionnant deux fois la touche directionnelle positionner le curseur avant le
prompt. Vous pouvez alors commencer la slection de ce point si vous souhaitez
entre autres eacer tout le groupe d'excution, prompt compris.
Conseil 6 Prenez l'habitude pour les eacements un peu complexes de slectionner d'abord, la souris ou au clavier, la zone eacer. Ceci fait vous pouvez
alors procder l'eacement ou encore un coup ou un copi pour un coll ultrieur.
Vous pouvez aussi eacer un paragraphe l'aide de la combinaison <CtrlSuppr> ; c'est quelquefois assez commode pour supprimer rapidement de grandes
zones de texte. Se mer toutefois d'un pige : aprs la suppression, il est frquent
que le curseur ne soit pas positionn aprs le paragraphe supprim, mais plus loin,
ce qui est un peu dsagrable. Un paragraphe est une zone de texte source (Maple
Input) situe entre deux prompts, ou le rsultat d'une instruction, ou encore un
segment de texte commentaire disjoint du texte source Maple.
36
..................................................................................................................................
..................................................................................................................................
end ;
..................................................................................................................................
..................................................................................................................................
Mais qu'est-ce qui peut expliquer ces trangets ? On a tout compris quand on
sait que le caractre en n de ligne qu'on croyait tre un espace tait en fait un
sparateur de lignes, souvent appel retour chariot (Endline ou Return20 selon
la terminologie anglaise). Supposons donc que le curseur soit positionn en n de
ligne derrire ce caractre dguis en espace ; alors :
1. Si vous entrez un BackSpace, vous supprimez le sparateur de lignes et la
ligne suivante vient donc se positionner la n de la ligne en cours !
2. Si au contraire vous entrez un caractre banal, il est entr droite du sparateur de lignes, donc sur la ligne suivante !
C'est d'une logique imparable, au moins quand on sait. Que fallait-il donc faire
pour insrer notre parenthse diabolique la bonne position ? Il fallait, aprs avoir
positionn le curseur en n de ligne l'aide de la touche Fin, utiliser la touche
directionnelle pour positionner le curseur avant le sparateur de lignes ; on
peut alors enn entrer la parenthse l o c'est ncessaire.
On vous conseille de consacrer l'occasion un quart d'heure ou une demi-heure
pour bien comprendre ces mcanismes. Une technique vous aidera grandement. Le
20 L'analyse
des chiers Maple montre que ce n'est en fait ni l'un ni l'autre, car Maple a ses
propres mthodes de codage pour les sparateurs de lignes.
37
bouton
de la barre d'outils rend visibles les caractres normalement invisibles
sur votre feuille de travail. Les phnomnes sotriques expliqus longuement dans
cette section seront alors trs clairs. Dans le mme registre, vous pouvez ainsi voir
que les touches <Entre> et <-Entre> ne produisent pas du tout le mme
rsultat.
Undo et redo.
Il est assez frquent qu'on souhaite dfaire ce qu'on vient de faire, surtout
quand ce qu'on vient de faire est une suppression, auquel cas il s'agit plutt
de refaire ce qu'on vient de dfaire. . . La commande Undo du menu Edit est
prvue cet eet. Le raccourci clavier Ctrl-Z est commode pour la rptition
de cette commande, autrement dit pour continuer dfaire ; mais la mmoire de
Maple dans ce registre est assez rduite. On peut inverser le mcanisme avec la
commande Redo.
Trouver.
La commande Find du menu Edit ouvre une fentre de dialogue vous demandant quelle chane de caractres vous voulez chercher ; le raccourci Ctrl-F est
disponible. Quand le texte chercher est dni dans la mini-fentre, vous avez
encore le choix de chercher en avant ou en arrire.
Cette technique est utile quand votre feuille de travail devient importante et
que vous n'avez pas une mmoire prcise du point o par exemple une modication doit tre eectue. C'est aussi un outil bien commode pour l'exploration des
feuilles d'aide un peu vastes ; on s'y sent souvent un peu noy dans la multitude
d'indications techniques concernant les nombreux cas d'utilisation prvus ; pensez
alors Ctrl-F : ce peut tre le moyen de localiser rapidement l'information qui
vous intresse.
Noter que la recherche n'est pas possible de cette faon dans les rsultats des
calculs (Maple output). C'est dommage, mais quand ceci devient quasiment indis38
pensable, par exemple pour rechercher l'occurence de telle chane dans un rsultat
euve occupant plusieurs dizaines d'crans, vous pouvez procder comme suit.
Choisissez l'option Maple Notation (menu Options, option Output Display),
et faites rexcuter l'instruction critique. Le rsultat est alors ach sous forme
d'une chane ASCII o la recherche devient possible. Vous pouvez ensuite revenir
l'option Standard Math Notation pour revenir aux achages sorties Maple
standard.
Comparer par exemple les achages suivants ; dans le premier cas, si l'achage
rsultat est Standard Math Notation, la recherche de la chane de caractres
Pi est inoprante :
le rsultat est beaucoup moins lisible, mais par contre la recherche de la chane Pi
russit. Dans ce petit exemple, la dirence est insigniante, mais, si, comme cela
arrive de temps en temps, un ou des rsultats occupent plusieurs crans, ce peut
tre le point cl pour localiser tel ingrdient particulier.
39
8 4 5 5 3 5 8 5 1 0
3 4 5 2 1 9 5 8
4 3
8
9
7
5
0
4
4
2
5 5
MM :=
9 9 4
0 8 5 4 7 9 5
7 8 3
5 9 4 0 1 5 5
..................................................................................................................................
Vous essayez la suite de votre dmonstration avec cette matrice tombe du ciel et
si elle correspond votre projet, vous pouvez vouloir donner l'impression que cette
matrice a t choisie par vous-mme ! Il est assez fastidieux de recopier soi-mme
l'instruction Maple ad hoc :
..................................................................................................................................
..................................................................................................................................
Pour viter ce travail pnible, vous pouvez balayer la souris l'output (bleu)
M M := . . . ; un gros pav noir surcharge votre output qui apparat maintenant
en jaune sur fond noir. Vous actionnez la combinaison clavier Ctrl-C ou CtrlInsert pour copier ce qui est slectionn dans ce que Microsoft-France appelle
le presse-papiers, actionnez ensuite Ctrl-J pour faire apparatre un nouveau
groupe d'xcution, puis Ctrl-V ou -Insert pour y copier le contenu du pressepapiers ; vous obtenez ainsi aprs quelques manuvres videntes d'dition quelque
chose comme :
..................................................................................................................................
> MM := matrix(
[[8, 4, -5, -5, 3, -5, 8, 5, -1, 0],
[3, -4, -5, -2, -1, -9, 5, 8, 4, -3],
[8, -9, 7, 5, 0, 4, 4, 2, 5, -5],
[9, -9, 4, 0, -8, -5, 4, 7, -9, 5],
[7, -8, 3, 5, -9, 4, 0, -1, -5, 5]]) ;
..................................................................................................................................
nant l'impression que cette matrice a t choisie par vous-mme ! Cette technique
est quelquefois abolument indispensable quand la gnration devient vraiment ( !)
alatoire, par exemple quand on utilise la procdure randpoly pour la gnration
de polynmes alatoires.
On rutilisera cette technique de copie output input page 47 pour une
autre raison qui sera explique alors, essentiellement pour mettre en vidence la
dirence entre format externe d'un objet et objet proprement dit.
-o-o-o-o-o-o-o-
41
Chapitre 2
Le modle Read-Eval-Print de
Maple
2.1 Pourquoi un modle ?
L'architecture des grands logiciels n'est pas simple, leur utilisation non plus.
Mais la formation leur utilisation l'est encore moins ! On entend dire souvent,
quand il s'agit par exemple de planier un cours Maple semestriel, qu'on s'organisera pour se dbarrasser rapidement des technicits informatiques et aborder aussi
vite que possible la seule partie noble de cet enseignement, celle qui est consacre
aux vraies mathmatiques. Ceux qui tiennent ce discours ne savent pas de quoi
ils parlent.
L'utilisation srieuse de Maple, comme celle de tous les logiciels d'envergure, y
compris les plus populaires, ncessite une initiation informatique ne ngliger sous
aucun prtexte. L'outil usuel pour ce faire consiste prsenter, explicitement ou
implicitement, un modle de fonctionnement. Le modle est une version abstraite
ultra-simplife du logiciel permettant de dcrire de faon aussi lmentaire que
possible les grandes lignes de sa structure. Un logiciel a un noyau (kernel) qui
est en quelque sorte son cur1 . Le modle est de faon analogue le noyau de son
apprentissage. On utilisera ici le modle Read-Eval-Print, selon la terminologie
devenue usuelle pour prsenter la structure du fonctionnement de la machine Lisp.
2.2 Read-Eval-Print.
2.2.1 Cycle Input-Output.
L'utilisateur de Maple voit d'abord un cycle Input-Output. Pendant la phase
Input, il entre au clavier une instruction Maple ; cette phase est termine par l'entre d'un ; et de <Entre>. La phase Output est alors lance, se terminant
1 Un
42
dans les bons cas par l'achage juste aprs l'instruction entre du rsultat obtenu. Un nouveau groupe d'excution est ouvert, et le curseur est positionn juste
aprs le prompt. Une nouvelle phase Input commence o l'utilisateur va entrer son
instruction suivante, etc.
..................................................................................................................................
> 4 ;
4
..................................................................................................................................
x2 dx = x2
. . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . x
............................................................................
Mais par rapport au modle qu'il s'agit de dcrire, ces considrations sont
secondaires.
R
Le calcul de l'intgrale 1 1+x1+x
2 +x4 dx demande sur un PC de puissance moyenne
environ une demi-seconde de calcul, et c'est prcisment l que Maple est utile.
C'est la phase d'valuation. L'valuateur Maple a considr l'Input entr par l'utilisateur (plonasme) ; l'valuateur tait missionn pour l'valuer. C'est un travail
qui peut tre trs bref, comme plus haut quand il s'agissait d'valuer l'Input 4 ;
Maple constate alors presque instantanment qu'il n'y a aucun travail digne de
ce nom eectuer, et il retourne aussitt l'Output 4 ; c'tait trs bref, mais
il est quand mme capital pour la suite de comprendre qu'il y a bien eu une
phase d'valuation. Au contraire, pour le calcul de l'intgrale, la phase d'valuation est fort complexe : de nombreuses recherches doivent tre faites par Maple
pour comprendre qu'il doit eectuer une intgration, qu'il doit examiner la nature
de l'intgrande, voir si l'intgrale est dnie ou indnie, adopter une stratgie
pour trouver une primitive, la mettre en uvre, etc. C'est un travail sophistiqu,
mettant en uvre des ressources trs varies, mais peu importe, tout ceci est quand
mme une phase d'valuation.
43
2.2.2 L'valuateur.
Il est donc indispensable d'enrichir le cycle Input-Output pour en faire un cycle
trois temps que, compte tenu d'une trs ancienne tradition provenant de Lisp, on
prfre appeler le cycle Read-Eval-Print. Cette terminologie a un autre avantage,
elle prend dnitivement le point de vue de Maple. Maple apparat comme un chef
d'orchestre avec trois excutants :
1. Le Lecteur : c'est la composante de la machine Maple charge de lire le
texte entr par l'utilisateur, autrement dit l'Input. Le paradoxe usuel, si
coriace pour les super-dbutants, est toujours l ; l'utilisateur a l'impression
au contraire d'crire, mais son point de vue ne nous intresse pas ; on ne veut
considrer que le point de vue de Maple, qui doit bel et bien lire un objet
Maple, appel Input, savoir l'objet crit par l'utilisateur. Le Lecteur est
l'excutant consacr cette tche.
2. L'valuateur : c'est vraiment le cur de Maple ; l'valuateur doit valuer
l'objet Maple que le Lecteur vient de lire. Ce peut tre un travail quasiinstantan ; inversement il peut l'occasion ncessiter plusieurs jours de
calcul ; peu importe, c'est une valuation et c'est l'valuateur qui en est
l'excutant.
3. L'Imprimante qu'il est plus raisonnable dans le contexte d'aujourd'hui
d'appeler l'Acheur : une fois que l'valuateur a termin son travail, l'Acheur doit faire le ncessaire pour acher le rsultat de l'valuation l'cran,
rsultat obtenu par l'valuateur. C'est un travail assez technique, peu important en thorie, trs dlicat en pratique, mais absolument indispensable sans
quoi le travail de l'valuateur serait perdu. L'Acheur est ddi cette troisime phase.
On a dj utilis sans explication une terminologie qu'il est temps d'claircir. L'valuateur travaille en fonction de l'expression (Input) qu'il doit valuer.
Quand il a termin son travail, on dit qu'il retourne le rsultat, c'est l'Output
que l'acheur doit maintenant acher. Cette terminologie est devenue usuelle en
informatique, mais l'exprience montre qu'elle trouble encore beaucoup de mathmaticiens, et non des moindres. . . Pour la justier, il faut penser que l'valuateur
est un correspondant qui reoit, disons par la Poste, une lettre lui commandant tel
ou tel travail ; quand le travail est excut, l'valuateur en retourne le rsultat au
demandeur, en fait par l'intermdiaire de l'acheur. En particulier il ne s'agit pas
d'un refus retour l'expditeur ! La commande est en gnral honore et ce qui est
retourn est au contraire, au moins les bons jours, ce qui est souhait !
Maple se contente de faire travailler les trois excutants Lecteur, Evaluateur
et Acheur tour de rle. Compte tenu de cette organisation en cycles ReadEval-Print, l'utilisateur de Maple doit organiser son travail sous forme d'une suite
d'valuations d'objets dnir en fonction du problme rsoudre. Le travail de
comprhension de Maple se partage donc paralllement en trois parties.
1. On doit savoir comment travaille le Lecteur de Maple ; bien entendu la
connaissance de la structure interne du lecteur ne nous intresse pas ; par
contre nous devons connatre les mcanismes permettant de dcrire l'objet
44
Peu importe ce que sont les objets composants obj0, . . ., objn, notre objet compos est un objet function propos duquel des rgles universelles de construction,
d'valuation et d'achage sont applicables. Les dirents composants sont des objets quelconques ; ils peuvent tre leur tour, pourquoi pas, des objets function,
ou bien des objets d'autres types qu'on tudiera le moment venu, il y en a une
grande varit. Dans notre exemple, le composant obj0 est l'objet symbol3 int,
le composant obj1 est l'objet *4 (1+x)/(1+x2+x4), enn le dernier composant obj2 est l'objet equation x=1..infinity. Autrement dit tout type de donne
va donner lieu la description des objets de ce type comme constitus d'objets
composants, en gnral quelconques, assembls selon des rgles ne dpendant que
2 Les
questions de types sont importantes ; on utilise pour le souligner une police un peu
sophistique pour les noms de types ; choisis par les concepteurs de Maple, ce sont des noms
anglais.
3 Ainsi symbole quivaut objet symbol.
4 de rares exceptions prs, Maple code de faon interne les quotients A/B comme le produit
(A1)*(B(-1)), de sorte que pour Maple ces objets qui extrieurement paraissent tre des
quotients sont en fait des produits, de type *.
45
du type de donne en question. Certains types sont terminaux, on les appelle atomiques : ce sont des objets irrductibles en plus petits objets. Les symboles sont
de cette nature.
Ce mcanisme est trs bnque. Il va donc s'agir en dnitive de bien connatre
les types de donnes disponibles, qu'on peut considrer comme des constructeurs
lmentaires, capables de construire partir d'autres objets, simples ou complexes,
peu importe, un nouvel objet certainement plus complexe. Pour chaque type de
donne, il va falloir connatre sa structure interne ; mais un modle thorique pour
cette structure interne, plus commode, sura ; il va falloir aussi connatre sa forme
externe, autrement dit comment on peut prparer un tel objet comme une chane
de caractres qu'on donnera en Input au lecteur Maple pour qu'il construise eectivement l'objet souhait, en vue de son valuation . Le plus souvent on retrouvera
la mme forme externe l'achage, si un objet de ce type est un rsultat d'valuation ; cependant, pour le dernier point, un achage plus proche des habitudes des
mathmaticiens est souvent prfr. Considrons par exemple l'intgrale prpare
pour le Lecteur plus haut ; il pourrait se faire que cette intgrale (non value) soit
au contraire le rsultat d'une valuation, auquel cas elle serait alors ache :
..................................................................................................................................
Z
1+x
dx
1
+
x2 + x4
. . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .1. . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
mais ces dirences entre forme externe lire et forme externe ache sont assez
secondaires.
Faisons cette petite exprience. Soit l'instruction :
..................................................................................................................................
..................................................................................................................................
On a entr nouveau notre intgrale ftiche, ceci prs qu'elle est maintenant
quote : le premier et le dernier caractre sont maintenant des quotes, c'est--dire
des apostrophes ou, si on prfre, des accents aigus isols. L'anglicisme quote est
laid, mais sa smantique est si particulire qu'on prfre l'utiliser. Il s'agissait ici
d'empcher l'valuation de l'intgrale et, comme on l'observe l'cran, l'intgrale
est retourne telle quelle, sauf qu'elle apparat sous la forme typographique usuelle
des manuels de mathmatiques. Notre exprience consiste nous dmontrer que
la forme interne est bien la mme. Pour ce faire on amne la souris sur le rsultat
qui vient d'tre obtenu, et on slectionne ce rsultat par la manuvre usuelle de
balayage : la belle intgrale est maintenant dessine en jaune dans un rectangle
noir ; Maple fait plus, il ache dans une mini-fentre de la barre contextuelle, la
forme dite Maple-Notation de la mme intgrale ; on l'a souligne par une che
rouge dans la reproduction ci-dessous :
46
On voit que cette forme Maple-Notation n'est autre que notre Input, ceci
prs que les quotes d'encadrement ont disparu. On dtaillera ce point un peu plus
loin5 . On demande un copi de cette intgrale, par exemple par Ctrl-Insert. On
positionne ensuite le curseur au prompt en attente et on demande cette fois un coll,
par exemple par <-Insert>. On voit alors apparatre l'intgrale sous la forme ncessaire pour un Input, une chane de caractres rouges int((1+x)/...infinity),
celle qu'on a dj vue plusieurs fois :
Eval-10
47
sous deux formes externes assez direntes en apparence, quivalentes sur le fond.
L'opration copi aurait aussi bien pu tre eectue dans la fentre contextuelle.
On peut mettre en vidence la sparation du travail entre Lecteur et Evaluateur d'une part, Evaluateur et Acheur d'autre part, comme suit. Considrons
l'expression absurde suivante, dont prudemment on empche d'abord l'valuation
(quotes) :
..................................................................................................................................
Z
sin(x)d[1, 2, 3]
> % ;
Error, (in int) wrong number (or type) of arguments
..................................................................................................................................
L'intgrale est une expression qui, sans convention pralable, n'a pas de sens.
Mais c'est un objet Maple lgal, que le Lecteur de Maple sait lire, que l'Acheur
sait acher. L'instruction suivante demande l'valuation de cet objet ; l'valuateur
ne peut traiter cette intgrale et retourne donc un message d'erreur.
restera inconnue de l'utilisateur, mais elle pourra tre cite indirectement l'aide
du symbole n. Si la dclaration est locale une procdure appele dynamiquement,
l'adresse relle machine est en gnral variable d'une invocation l'autre de la procdure, mais le mcanisme d'adressage symbolique dispense justement l'utilisateur
des technicits sous-jacentes : elles sont gres par le systme.
Ce mcanisme d'adressage symbolique s'est son tour montr insusant. Les
mthodes d'indirections dynamiques utilises en langages machines et assembleurs
depuis longtemps taient inaccessibles aux utilisateurs de langages dits volus
comme Fortran6 . Pour y remdier, on a imagin un nouveau type de donne, celui
de pointeur : un symbole de type pointeur reprsente une case mmoire contenant
l'adresse d'une autre case mmoire. Les mcanismes satellites d'allocation mmoire
avec mise jour d'un pointeur vers l'adresse de la zone mmoire alloue permettent
de nouvelles techniques de programmation trs puissantes, traitements de listes et
d'arbres notamment. Les langages PL/I puis Pascal ont t les premiers langages
populaires ayant parfaitement intgr ce type de donnes.
Les langages plus modernes, Lisp notamment7 , sont alls plus loin. Par une
organisation soigneuse des types de donnes disponibles, la notion de pointeur y a
t en apparence compltement supprime, alors qu'en fait les pointeurs y sont plus
prsents qu'ils ne l'ont jamais t ! C'est un point trs intressant de l'volution
des langages informatiques. L'ide cl est la suivante : compte tenu de l'importance
des pointeurs, au lieu de laisser l'utilisateur la libert de dcider quand un objet
est de type pointeur ou non, on organise le langage comme si tout objet tait
un pointeur potentiel ; c'est le systme sous-jacent qui prendra en dnitive les
dcisions ce propos. Typiquement, si un symbole n repre un entier, le systme
doit de toute faon rserver un mot mmoire pour n ; si la valeur de n est un
entier court, le systme peut dcider d'installer cet entier directement dans la
case rserve pour n ; si au contraire c'est un entier long ou trs long, le systme
dcide alors d'installer dans la case n l'adresse d'une liste contenant l'ensemble
de tous les ingrdients ncessaires pour dnir l'entier long en question ; quelques
bits systme sont rservs dans la case n pour indiquer quelle est la solution
utilise un instant donn. Ce type de mcanisme est devenu standard dans les
langages trs volus. L'utilisateur n'est d'ailleurs pas directement concern par
les techniques d'implmentation ; pour lui tout se passe comme si un symbole tait
toujours un pointeur.
C'est l'organisation adopte dans Maple. Un symbole est un pointeur vers un
objet de type quelconque, quelques variantes prs qu'on verra en temps utile.
Le couple [symbole objet point] est un chanage. L'ensemble de tous les
chanages en mmoire un moment donn est l'environnement en cours, et c'est
cet objet assez sophistiqu qu'il s'agit d'tudier dans cette section.
6 Les
versions rcentes de Fortran, depuis Fortran 90, disposent aussi du type pointeur ; la
notion de classe est prvue pour 2020 et la programmation fonctionnelle pour 2050.
7 Lisp est en fait un langage trs ancien, qui est n au dbut des annes 60, mais il n'est
devenu utilisable pour les grands projets qu'assez rcemment, depuis la dnition de la norme
ANSI Common Lisp.
49
2.3.2 Chanages.
Vocabulaire.
De bons petits exemples valent mieux que des tonnes de thorie. Considrons
cette micro-session Maple :
..................................................................................................................................
> x := 34 ;
x := 34
..................................................................................................................................
Voir un chanage.
Le lecteur souhaite probablement voir un chanage de l'environnement initial. Pour voir le chanage ventuel de source le symbole symb, il faut excuter
eval(symb, 1). Par exemple la mise en vidence du chanage [x 34] install
ci-dessus peut tre obtenue par :
..................................................................................................................................
> eval(x, 1) ;
34
..................................................................................................................................
Si, au dbut d'une session Maple vous voulez voir par exemple le chanage de
source le symbole sin, procdez de mme.
50
..................................................................................................................................
> eval(sin, 1) ;
readlib('sin')
..................................................................................................................................
La procdure sin sait calculer le sinus de nombres rels ou complexes. L'environnement initial contient ce qu'il faut pour faire savoir Maple, le cas chant,
que la procdure sin peut tre obtenue par chargement partir de la bibliothque
standard. Vous tes peut-tre tent par un exemple plus simple, consistant voir
par exemple la valeur de dans l'environnement initial, mais vous allez tre du :
..................................................................................................................................
> eval(Pi, 1) ;
..................................................................................................................................
Quand un symbole, d'aprs eval(..., 1), pointe vers lui-mme, c'est qu'en fait
ce symbole est absent de l'environnement, et c'est le cas du symbole Pi si important
pour les mathmaticiens ; noter au passage qu'on trouve ici aussi une situation o
l'unique objet interne, le symbole de nom Pi, a une forme externe input Pi assez
dirente de la forme externe output choisie par l'Acheur : . Mais o donc par
exemple est localise l'information que est peu dirent de 3.14 ? On l'obtient
par la procdure evalf :
..................................................................................................................................
> evalf(Pi, 4) ;
3.142
..................................................................................................................................
C'est donc le symbole evalf et non pas le symbole Pi qui est prsent dans l'environnement initial de telle faon que l'information 3.142 soit accessible ; le
deuxime argument 4 de evalf demandait une approximation quatre chires dcimaux. Bien noter que le fait que Pi soit absent de l'environnement ne signie pas
qu'il n'y soit pas rfrenc. C'est un point de terminologie important : un symbole
est prsent dans un environnement si et seulement s'il est la source d'un chanage.
On peut par exemple modier le chanage de source x par :
..................................................................................................................................
> x := Pi ;
x :=
..................................................................................................................................
de telle sorte que x pointe vers le symbole Pi ; le symbole Pi est donc dsormais
rfrenc, mais il reste absent de l'environnement. Le symbole Pi est libre, ce qui
est un peu trange par rapport son statut mathmatique ; ce sont les procdures
utilisatrices de Pi qui sont au parfum et sauront faire les calculs quelquefois
diciles que vous attendez. Vous pouvez aussi tre tent par :
..................................................................................................................................
> Pi := 355/113 ;
..................................................................................................................................
On voit que Pi est un symbole mieux que libre, il est protg ; en particulier vous
ne pouvez pas le rendre prsent dans l'environnement8 .
8
moins de lever la protection (unprotect), mais, sauf cas trs spcial, c'est franchement
dconseill !
51
> a := b ;
a := b
> b := c ;
b := c
..................................................................................................................................
> eval(a, 1) ;
> a ;
c
..................................................................................................................................
> c := d ;
c := d
> a ;
d
..................................................................................................................................
et ainsi de suite.
Warning 8 Si la valeur du symbole symb est l'objet obj dirent de symb, ceci
n'implique pas que le symbole symb pointe vers l'objet obj. La seule conclusion
correcte est la suivante : la valeur de l'objet obj2 point par symb est obj.
9 On
verra Chapitre 6 qu'il y a une rgle d'valuation particulire pour les paramtres de
procdures et leurs symboles locaux.
52
> restart ;
..................................................................................................................................
Ceci restaure l'environnement initial et en particulier dtruit les chanages prcdemment installs par l'utilisateur. Ne pas s'tonner de l'absence apparente d'output ; il y en a bien un mais c'est l'objet vide, dont l'achage est aussi vide ! Ce
point sera dtaill plus tard. Si vous demandez maintenant :
..................................................................................................................................
> a := a ;
a := a
..................................................................................................................................
l'environnement n'est pas modi ; c'est une convention : demander qu'un symbole pointe sur lui-mme, c'est demander conventionnellement de le librer10 . S'il
tait dj libre, l'environnement n'est donc pas modi. Prenons maintenant au
contraire le cas o le symbole a serait prsent :
..................................................................................................................................
> a := b ;
a := b
..................................................................................................................................
> a := a ;
a := b
> a ;
b
..................................................................................................................................
Vous avez ici la surprise de voir qu'aprs avoir demand (input) que a pointe
vers a, Maple dcide de le faire pointer. . . vers b, comme le montre l'output ! Que
comprendre ? Il y a ici un autre point de rcursivit trs important.
Eval 9 Une instruction d' aectation symb := obj est excute en deux
temps :
1. L'objet obj est valu et, si cette valuation termine, elle retourne un objet
obj2 ;
2. Un chanage [symb obj2] est install dans l'environnement. Si le symbole
symb tait dj prsent dans l'environnement, le chanage antrieur est retir.
C'est pourquoi, dans la commande qui semblait si innocente a := a, Maple
a d'abord valu le second membre a et l'valuateur a retourn b ; Maple dcide
donc d'aecter b a comme le montre ce qui est indiqu par l'acheur ; en dnitive la situation reste inchange : l'ancien chanage est dtruit, mais le mme est
10 Voir
53
aussitt rinstall ! D'une faon gnrale, une instruction symb := symb modie
l'environnement comme suit : le chanage de source symb est redni pour pointer
vers la valeur actuelle de symb. L'exprience ad hoc est la suivante.
..................................................................................................................................
> restart ;
a := b ; b := c ; c:= d ;
a := b
b := c
c := d
> eval(a,1) ;
a ;
b
d
> a := a ;
a := d
> eval(a,1);
a ;
d
d
..................................................................................................................................
Eval 10 L'valuation d'une expression quote 'expr' retourne l'objet expr non
valu, quotes retirs.
..................................................................................................................................
> a := 'a' ;
a := a
> a ;
a
..................................................................................................................................
> a := b ; b := a ;
a := b
b := b
..................................................................................................................................
> restart ;
> a := b ; b := 'a' ;
a := b
b := a
..................................................................................................................................
54
Et cette fois on a bien install un cycle d'ordre 2 dans les chanages. On peut
dans ces conditions, compte tenu de la rcursivit de l'valuation des symboles (cf.
Eval-7), tre assez perplexe sur le rsultat de l'valuation de a (ou b). Maple aussi :
..................................................................................................................................
> a ;
..................................................................................................................................
C'est notre premier exemple d'une valuation qui ne termine pas. Les deux chanages rciproques [a b] et [b a] provoquent une rcursivit sans terminaison de l'valuateur. Le rsultat obtenu dpend du systme sous-jacent ; le
message d'erreur ach ici est obtenu sous Windows ; sur certains systmes Unix,
aucun message d'erreur n'est ach ; de plus l'valuation indnie ne peut mme
pas tre interrompue de l'intrieur de Maple par le bouton stop ; la seule solution
est l'interruption extrieure, par exemple par la commande Unix kill mise par
un autre process ; mais la session Maple est perdue !
> restart ; a := b ; b := c ; b := d ;
a, eval(a, 1) ;
a := b
b := c
b := d
d, b
> restart ; b := c ; a := b ; b := d ;
a, eval(a, 1) ;
b := c
a := c
b := d
c, c
..................................................................................................................................
On voit que l'ordre des aectations est important. Dans le premier cas, b est aect
a avant que c soit aect b ; compte tenu de l'aectation de d b, il en rsulte
que la valeur de a est d, dirente de l'objet point par a. Dans le second cas,
les deux premires aectations sont changes ; l'aectation demande a := b
aecte donc la valeur de b, soit c, a ; le nouveau chanage install pour b ne
modie donc pas la valeur de a.
Le lecteur est normalement troubl par les virgules sparant a de eval(a, 1),
alors qu'on devrait sparer par un point-virgule les deux instructions demandant,
la premire, l'valuation de a, la seconde, l'valuation de eval(a, 1). On verra
par la suite qu'en fait le texte a, eval(a, 1) est la forme externe d'un unique
objet Maple deux composants ; en Maple, la virgule n'est pas un sparateur,
c'est un oprateur constructeur de suites. Ces notions seront dtailles plus loin
55
Chapitre 4. Pour le moment, vous pouvez considrer qu'est ainsi disponible une
mthode permettant d'acher deux objets Maple ou plus sur une seule ligne. Par
contre vous ne pouvez faire de mme avec deux instructions d'aectation, car ces
instructions ne sont pas des objets Maple.
..................................................................................................................................
> a := 1 , a :=
| 2 ;
`:=` unexpected
..................................................................................................................................
..................................................................................................................................
Il faut en particulier utiliser une variable libre, ici x, pour faire savoir Maple
par rapport quelle variable l'intgration doit tre eectue, et aussi, s'il s'agit
d'une intgrale dnie, quel est l'intervalle d'intgration. Pour Maple, cette variable libre est en fait un symbole, mais par abus de langage, tenant compte aussi
du contexte mathmatique, on parle souvent de variable libre. Toujours est-il
que ce symbole doit tre eectivement libre, sous peine d'erreur assez souvent rebelle. Le scenario est habituellement le suivant ; on fait pendant un moment de
petits calculs et il est alors tentant, quand on souhaite conserver pour un temps
une valeur numrique un peu complique de l'aecter un symbole quelconque,
pourquoi pas x. Par exemple la valeur numrique de la fonction en 1/3 pourrait
tre utilise de faon un peu rptitive et pour viter de devoir retaper chaque
fois evalf(GAMMA(1/3)), vous pouvez choisir de demander :
..................................................................................................................................
> x := evalf(GAMMA(1/3)) ;
2.678938537
..................................................................................................................................
Bien ! Eectivement la session Maple volue, la question faisant intervenir ponctuellement la quantit (1/3) est traite, on passe la suite du plan de travail ; les
divers sujets se succdent et quelquefois beaucoup plus tard, mais dans la mme
session, on doit valuer l'intgrale eulrienne indique plus haut.
..................................................................................................................................
..................................................................................................................................
..................................................................................................................................
..................................................................................................................................
Une lecture correcte de l'objet valu va comme suit : la liste des i2 pour ($ =
pour) i variant de 10 20. La liste en question est eectivement retourne.
Comme tout langage impratif, Maple propose des instructions itratives. Par
exemple pour acher les valeurs de l'intgrale de 1/(1+x3 ) entre 0 et les premires
puissances de 10, on pourrait demander :
57
..................................................................................................................................
..................................................................................................................................
Mais si, ceci fait, vous demandez maintenant la construction de SquareList comme
ceci avait pourtant t russi auparavant :
..................................................................................................................................
..................................................................................................................................
vous obtenez une erreur trange. C'est le moment de penser Conseil-11 ; le seul
symbole suspect est i, et il faut donc l'examiner :
..................................................................................................................................
> i
6
..................................................................................................................................
..................................................................................................................................
qui est incohrente, car ce qu'on appellera plus tard la variable pilote pour la
procdure $ est ici l'entier 6, mais un entier n'est pas une variable ! Si on empche
(quotes) l'valuation de i :
..................................................................................................................................
..................................................................................................................................
cette fois la procdure $ peut travailler, mais l'valuation prmature du premier
terme i^2 ne donne pas le rsultat escompt ! Pour obtenir le bon rsultat, il faut
aussi quoter le premier i :
..................................................................................................................................
..................................................................................................................................
Conseil 12 En prsence d'une erreur rebelle, rchir si une valuation imprvue n'a pas impliqu l'invocation d'une procdure avec des arguments incorrects.
11 Contrairement
Lisp.
ce qui est maintenant standard, par exemple dans les langages C, Java et
58
2.4.1 Post-valuation.
Eval 13 Quand un rsultat d'valuation est obtenu, Maple examine si ce rsul-
tat est son tour non trivialement valuable. Si la rponse est ngative, le processus d'valuation est termin. Si au contraire la rponse est positive, le rsultat de
l'valuation sera en dnitive le rsultat de l'valuation du rsultat prcdemment
obtenu.
Il est clair que dans la deuxime hypothse aucune garantie ne peut tre obtenue sur la terminaison du processus d'valuation. L'exemple des deux chanages
rciproques [a b] et [b a] a montr qu'il peut eectivement arriver que
l'valuation ne termine pas. Pour illustrer la porte plus gnrale de Eval-13,
considrons la situation suivante. On fait pointer le symbole a vers la liste des
deux symboles b1 et c1 ;
..................................................................................................................................
> restart ;
> a := [b1, c1] ;
a := [b1, c1]
..................................................................................................................................
Ensuite on cre deux suites de chanages [b1 -> b2 -> b3] et [c1 -> c2 -> c3 ->
c4]. On verra page
les dtails concernant l'oprateur || (concatnation12 ) ;
les aectations rsultantes sont aches.
..................................................................................................................................
..................................................................................................................................
Ceci tant fait, grce aux procdures trs particulires seq et eval, dtails plus
tard, on peut acher les phases intermdiaires du processus d'valuation. On
ache ensuite le rsultat de l'valuation banale de a :
12 Jusqu'
59
..................................................................................................................................
..................................................................................................................................
> c4 := 'c2' ;
c4 := c2
> a ;
Error, too many levels of recursion
..................................................................................................................................
2.4.2 Pr-valuation.
La rgle Eval-13 indique qu'une valuation a posteriori est toujours tente. La
rgle d'valuation suivante demande au contraire une pr-valuation.
doit tre valu, l'oprateur obj0 et les oprandes13 obj1, . . ., objn sont valus
squentiellement avant d'tre utiliss. L'valuation de obj0 est de type explicite14
alors que l'valuation des autres arguments est de type implicite.
La rgle Eval-14 a de trs nombreuses exceptions, et son interprtation prcise
est assez dlicate, surtout quand il s'agit du traitement de l'oprateur obj0. Si
la valeur procdure de obj0 est une procdure non standard, le traitement des
oprandes peut tre trs dirent.
14 Voir
aussi arguments.
ce propos Eval-16.
60
..................................................................................................................................
.1155897239
..................................................................................................................................
> round(3.8) ;
4
..................................................................................................................................
..................................................................................................................................
> eval(Psi) ;
..................................................................................................................................
Raisonnablement, Maple prfre n'acher que sous une forme trs simplie l'objet procedure valeur, vous faisant grce du texte source fort complexe. L'valuateur observe que cette procdure est standard 15 et qu'elle est invoque avec
deux arguments ; le premier, appel obj1 dans la rgle Eval-14 est l'expression
round(tan(2.5)), le second, obj2, est l'expression sin(5.1). La terminologie suivante sera systmatiquement utilise dans la suite, elle est particulirement commode pour dcrire le fonctionnement de la rgle Eval-14 dans un cas particulier.
L'expression round(tan(2.5)) est le premier argument provisoire ; de la mme faon, l'expression sin(5.1) est le deuxime et dernier argument provisoire. La rgle
Eval-14 explique que ces arguments doivent tre valus avant d'tre utiliss. Les
rsultats de ces valuations seront les arguments dnitifs , ceux avec lesquels la
procdure Psi va eectivement travailler.
C'est ce point que l'valuateur est rcursif. L'exemplaire de l'valuateur qui
tait en activit pour traiter l'valuation principale est mis provisoirement au repos. Un deuxime exemplaire de l'valuateur est invoqu pour eectuer l'valuation
ncessaire de notre argument provisoire round(tan(2.5)). Pour cette invocation,
de nouveaux ingrdients sont identis ; l'oprande obj0 est cette fois le symbole
round, l'unique argument obj1 est l'expression tan(2.5). Cet argument, provisoire,
doit aussi tre valu avant d'tre utilis, etc. Le schma complet de l'valuation
est donc le suivant :
Eval1(Psi(round(tan(2.5)), sin(5.1)))
obj0p = Psi
15 Dans
de nombreux cas qui seront examins plus tard, la procdure est non-standard et les
arguments ne sont pas traits de la mme faon.
61
Eval2(Psi)
Eval2 -> procedure(Psi)
objOd = procedure(Psi)
obj1p = round(tan(2.5))
Eval2(round(tan(2.5)))
obj0p = round
Eval3(round)
Eval3 -> procedure(round)
obj0d = procedure(round)
obj1p = tan(2.5)
Eval3(tan(2.5))
obj0p = tan
Eval4(tan)
Eval4 -> procedure(tan)
obj0d = procedure(tan)
obj1p = 2.5
Eval4(2.5)
Eval4 -> 2.5
obj1d = 2.5
procedure(tan) works with 2.5
Eval3 -> -.7470222972
obj1d = -.7470222972
procedure(round) works with -.7470222972
Eval2 -> -1
obj1d = -1
obj2p = sin(5.1)
Eval2(sin(5.1))
obj0p = sin
Eval3(sin)
Eval3 -> procedure(sin)
obj0d = procedure(sin)
obj1p = 5.1
Eval3(5.1)
Eval3 -> 5.1
obj1d = 5.1
procedure(sin) works with 5.1
Eval2 -> -.9258146823
obj2d = -.9258146823
procedure(Psi) works with -1 and -.9258146823
Eval1 -> 2.639819868+3.141592654*I
On a utilis quelques conventions assez videntes pour ne pas tre envahi par
l'achage de tout ce qui serait en principe ncessaire. Chaque invocation de l'valuateur correspond une squence :
Evaln(expr)
...
...
Evaln -> ...
o en entre gure l'expression valuer et en sortie l'objet retourn par l'valuation. Quand cette invocation est active, l'invocation prcdente est mise au repos.
Une indication comme obj1p = ... indique qu'un composant avant valuation
62
est identi, p pour provisoire ; symtriquement une indication obj1d = ...
indique le mme composant aprs valuation, d pour dnitif. Enn une indication comme procedure(sin) note de faon symbolique l'objet procedure associ
au symbole sin, en gnral trs complexe.
On voit que le mcanisme d'valuation rcursive d'un objet function suit une
chronologie trs prcise et relativement complexe. L'objet valuer est d'abord dstructur pour obtenir les dirents composants. Le plus souvent, ces composants
sont valus avant d'tre utiliss, auquel cas le mcanisme en cours de description
s'applique son tour, rcursivement, aux composants. Quand les versions dnitives des composants sont obtenues, la procdure valeur du composant obj0
travaille enn avec les arguments dnitifs.
Il peut se faire que la valeur de obj0 ne soit pas une procdure mais par exemple
un symbole. Le mcanisme sera exactement le mme, ceci prs que la dernire
tape travail de la procdure est omise.
..................................................................................................................................
> restart ;
> f:= g ; g := h ; f(round(tan(2.5)), sin(5.1)) ;
f := g
g := h
h(1, .9258146823)
..................................................................................................................................
> Psi
> eval(Psi) ;
> eval(Psi, 1) ;
Psi
..................................................................................................................................
On voit grce au dernier essai que le chanage du symbole Psi vers la procdure
prdnie associe est bien l, mais l'valuation banale de Psi semble ne pas tenir
63
compte de ce chanage.
Par dfaut, l'valuation d'un symbole est implicite ; elle est explicite dans deux
circonstances :
1. L'valuation est demande par l'intermdiaire de la procdure eval ;
2. Le symbole est valu en position oprateur d'une expression fonction ou
objet index.
On verra plus tard le cas des objets indexs. L'exemple compltement articiel
suivant illustre le cas des objets function :
..................................................................................................................................
35
> eval(f1) ;
> f1(f2) ;
f2
> % ;
f2
> %(exemple) ;
2 exemple
..................................................................................................................................
Les deux procdures aectes f1 et f2 sont analogues ; elles retournent respectivement l'unique argument pass ou son double. On voit que l'valuation de
f1(35) a bien fait intervenir la procdure, car le symbole f1 est en position oprateur. Par contre l'valuation de f2 seul est implicite et la procdure but n'est
pas retourne. Dans l'valuation de f1(f2), l'valuation de f1 est explicite, alors
que celle de f2 est implicite, d'o le rsultat. Le pseudo-symbole % (objet ditto)
chane toujours vers le dernier rsultat obtenu, mais l'valuation est implicite et
l'valuation s'arrte donc f2. Enn dans la dernire expression, puisque % est
en position oprateur, l'valuation est explicite et la procdure valeur de f2 va
travailler, d'o le rsultat.
Un tel exemple est compltement articiel et a pour seul intrt de mettre
en vidence le mcanisme de fonctionnement de la rgle Eval-16. Il illustre aussi
comment justement concevoir des exemples articiels trs simples permettant de
dvisser le fonctionnement de l'valuateur.
64
..................................................................................................................................
Attention, la procdure type est standard et value donc ses arguments avant
de les utiliser ; si donc vous essayez :
..................................................................................................................................
..................................................................................................................................
pour voir si l'expression tudie dans la section prcdente est bien un objet
function, la rponse est ngative, car l'expression est d'abord value ; le rsultat
est un nombre complexe et un nombre complexe n'est pas un objet function. Il
faut comme toujours quoter pour empcher l'valuation.
..................................................................................................................................
..................................................................................................................................
Noter qu'un objet peut tre de plusieurs types dirents. Chaque type est un
ensemble d'objets Maple et en gnral ces ensembles ont des intersections non
triviales ; par exemple un entier (type integer) est aussi un rel (type realcons) :
..................................................................................................................................
..................................................................................................................................
65
..................................................................................................................................
..................................................................................................................................
Il est lgal de prsenter la mme expression sans les crochets ouvrant et fermant,
auquel cas on construit une suite :
..................................................................................................................................
..................................................................................................................................
Les dtails sur ces types itratifs trs importants seront tudis Chapitre 4. Il avait
t expliqu Section 2.3.3 pourquoi les mcanismes de prvaluation pouvaient
compliquer la vie si le symbole i tait prsent dans l'environnement. La similitude
avec ce qui est nonc dans la rgle Eval-14 suggre que l'expression ci-dessus
construite partir de l'oprateur binaire $ est aussi un objet function. C'est
bien le cas :
..................................................................................................................................
true
..................................................................................................................................
On peut d'ailleurs prsenter cette expression d'une faon plus fonctionnelle ; les
backquotes (accents graves) encadrant le $ initial sont indispensables :
..................................................................................................................................
..................................................................................................................................
La forme interne des deux objets prsents Maple, forme inxe ou forme prxe, est la mme. C'est le Lecteur de Maple qui fait le travail ncessaire pour
reconnatre l'une quelconque des deux formes et construire de toute faon sous
forme fonctionnelle l'objet dcrit. Pour en avoir le cur net, comparons les deux
objets :
..................................................................................................................................
..................................................................................................................................
police tltype utilise par LATEX est assez dcevante de ce point de vue : il faut tre
trs attentif pour distinguer les accents aigus des accents graves, autrement dit les quotes des
backquotes.
66
..................................................................................................................................
..................................................................................................................................
true
:= I'm not visible
..................................................................................................................................
..................................................................................................................................
false
..................................................................................................................................
Les deux possibilits existent, produisent presque toujours le mme rsultat, mais
les formes internes sont cette fois direntes ; l'oprateur Maple + inx est
trs particulier et en particulier l'objet correspondant n'est pas un objet function ;
comparer les deux rsultats :
..................................................................................................................................
false
true
..................................................................................................................................
Ces considrations ne sont pas l du tout pour vous apprendre les dirences
ventuelles plutt subtiles, quand elles existent, entre les formes inxes et les
formes prxes ; il est rarissime que ces dtails soient de quelque utilit. Il s'agit
seulement d'explorer un peu notre espace de travail, de fouiner, comme c'est la
rgle dans tous les grands logiciels. Seul l'utilisateur connaissant un peu la nature
gnrale de son espace de travail peut esprer y devenir un jour raisonnablement
autonome. Il s'agit dans ce manuel de vous expliquer Maple, et surtout de vous
rendre capable de trouver vous-mme les informations qui peuvent tre indispensables dans tel ou tel cas.
false
> a := 1 ; assigned(a) ;
a := 1
true
..................................................................................................................................
La procdure assigned est non-standard, car elle n'value pas son argument avant
de l'utiliser. Quand l'entier 1 est aect au symbole a, le symbole devient prsent
et la procdure assigned permet de le vrier. On retire ici a de l'environnement
en utilisant la convention explique page 53, par auto-aectation du symbole ;
on vrie ensuite, encore avec la procdure assigned, que le symbole a est bien
retir de l'environnement.
Le caractre non-standard de la procdure assigned est mis en vidence par
l'exprience suivante.
..................................................................................................................................
> restart ; a := b ;
a := b
true, false
..................................................................................................................................
> restart ; a := b ; b := 3 ;
a := b
b := 3
> unassign(a) ;
Error, (in assign) invalid arguments
..................................................................................................................................
Ce type d'erreur, assez frquente en mode interactif, est assez troublante pour
l'utilisateur non initi. La procdure unassign est standard et l'argument a est donc
valu avant d'tre utilis. Les deux chanages [a b] et [b 3] prsents dans
l'environnement impliquent que la valeur actuelle de a est l'entier 3, voir la rgle
Eval-7. Mais librer l'entier 3 n'a pas de sens, car la source d'un chanage ne peut
tre qu'un symbole, pas un entier. Par ailleurs le message d'erreur cite curieusement
68
> unassign('b') ;
..................................................................................................................................
Noter aussi que la procdure unassign semble sans valeur ; un nouveau prompt
apparat, mais aucun output n'est ach. Plus prcisment, on verra Chapitre 4
que l'output est la suite dite vide, un objet pas du tout vide, mais dont par
contre l'achage est bien vide !
Dans le cas prcdent on a utilis le fait qu'on savait que le symbole a pointait
vers b. supposer qu'on l'ait oubli, il faudrait valuer eval(a, 1) qui retournerait b, surtout pas a qui retournerait 3 ! Voir Section 50. Mais si unassign est
utilis au sein d'une squence de programmation, il faut savoir demander la libration du symbole point par a sans connatre d'avance le nom du symbole en
question. C'est justement le moment d'utiliser bon escient eval(..., 1), comme
illustr maintenant.
..................................................................................................................................
..................................................................................................................................
On voit que le symbole a est rest prsent, son chanage vers hidden_b n'a pas t
modi ; par contre le chanage de source hidden_b a t retir, ce qui peut aussi
tre vri comme suit.
..................................................................................................................................
true
f alse
..................................................................................................................................
Si enn on veut librer le symbole a, vous avez compris que ceci est inoprant :
..................................................................................................................................
true
..................................................................................................................................
car l'argument dnitif est hidden_b et c'est donc ce dernier qui est libr ; il tait
d'ailleurs dj libre. Pour librer le symbole a, il faut donc empcher l'valuation
de a comme argument de unassign :
69
..................................................................................................................................
false
a
..................................................................................................................................
..................................................................................................................................
Bien noter que l'unique argument de assign a t ici l'objet equation s = a, et
non pas l'instruction aectation s := a qui serait de toute faon illgale ; en
eet le texte s := a dnote une instruction et non un objet ; or un argument ne
peut tre qu'un objet. Au contraire le texte assign(s = a) est un objet et peut
par exemple tre aect un symbole :
..................................................................................................................................
..................................................................................................................................
> eval(obj, 1) ;
assign(s = a)
..................................................................................................................................
> obj ;
..................................................................................................................................
Ne pas croire que puisque rien n'est ach, rien n'est fait ! Comme la procdure
unassign, la procdure assign retourne la suite vide ; mais comme la procdure
unassign, l'invocation de la procdure assign modie l'environnement, cette fois
en y modiant ou en y ajoutant un chanage. Or ici on a demand l'valuation de
obj qui pointe vers assign(s = a) ; l'application de la rgle Eval-7 implique donc
que l'objet assign(...) doit tre valu ; le chanage [s a] est donc install
et le rsultat de l'valuation de obj est le rsultat de l'valuation de assign(...),
donc la suite vide, invisible.
On ne voit pas bien a priori l'utilit de la procdure assign par rapport
l'aectation ordinaire s := a ; mais la procdure assign est standard et value
donc ses arguments, ce qui est source de possibilits varies. Dans une squence
de programmation, il peut arriver par exemple qu'un symbole s pointe vers un
autre symbole variable d'un moment l'autre pendant l'excution ; il peut arriver
70
qu'une aectation soit souhaite pour le symbole point par s, ce que ne permet
en aucune faon l'aectation ordinaire.
..................................................................................................................................
> s := a ; s := 3 ;
s := a
s := 3
> s, a ;
3, a
..................................................................................................................................
> eval(s) := 3 ;
..................................................................................................................................
mais on voit que cette instruction produit une erreur, car aucune valuation ne
peut intervenir au niveau suprieur dans le membre de gauche d'une instruction
d'aectation. Il faut, si on veut aecter au symbole valeur de s par exemple l'entier 3, utiliser la procdure assign :
..................................................................................................................................
> restart ; s := a ;
s := a
> assign(s = 3) ;
> eval(s, 1) ; eval(a, 1) ;
a
3
..................................................................................................................................
a
33
..................................................................................................................................
On espre que le lecteur comprend quel point ces jongleries exigent une
lucidit parfaite sur les mcanismes d'valuation, sous peine d'anarchie complte !
Mais inversement ces mcanismes ne sont quand mme pas si compliqus, et si
vous faites l'investissement appropri en la matire, le bnce est immense pour
les travaux un peu signicatifs.
71
Une autre cirsonstance o la procdure assign est bien utile, c'est quand la
valeur d'un symbole est un objet equation, autrement dit une quation. Ceci se
produit assez frquemment quand on travaille avec les solvers. Il peut arriver par
exemple qu'aprs avoir rsolu une quation, vous obteniez un rsultat quivalent
au suivant :
..................................................................................................................................
1 2
result := solution = e 12
..................................................................................................................................
Autrement dit la valeur du symbole result est maintenant l'quation dont le premier membre est le symbole solution et le second membre est l'expression math2
matique e /12 . Cette situation o la valeur d'un symbole est une quation o le
premier membre est son tour un symbole est en eet trs frquente. Vrions ce
point.
..................................................................................................................................
> result ;
1 2
solution = e 12
..................................................................................................................................
> assign(result) ;
..................................................................................................................................
> solution ;
1 2
e 12
..................................................................................................................................
Le fait que la procdure assign ne retourne rien est assez dsagrable, car
moins d'un supplment de votre part, vous ne pouvez pas vrier que l'aectation
souhaite est ralise ; or le cadre de travail o des mcanismes d'valuation assez
subtils risquent d'intervenir est assez dangereux.
Conseil 17 En mode interactif, aprs une instruction assign, vriez que l'affectation souhaite est bien ralise. Le mieux pour ce faire consiste demander
en plus l'excution d'une quation :
'symb' = eval(symb, 1) ;
solution = e 12
..................................................................................................................................
Bien distinguer dans ces questions l'instruction d'aectation := de l'oprateur quation =.
-o-o-o-o-o-o-o-
73
Chapitre 3
Les types de donnes numriques
3.1 Types, gnralits.
3.1.1 Les procdures type et whattype.
On a vu la n du dernier chapitre comment dterminer si un objet est d'un
type donn, l'aide de la procdure type.
..................................................................................................................................
..................................................................................................................................
On voit que le ottant 2. n'est pas un entier pour Maple. La procdure type examine la nature du codage qui est utilis pour l'objet dsign ; sa nature arithmtique
au sens mathmatique du terme n'est pas considre. Il aurait t plus prcis de
dire que 2. est un objet float mais n'est pas un objet integer.
Considrons dans le mme registre les instructions suivantes :
..................................................................................................................................
x := ( 5 1)( 5 + 1)
> type(x, integer) ;
false
..................................................................................................................................
La procdure type est standard et value donc ses arguments avant de travailler.
L'instruction ci-dessus, ne concerne donc pas le type du symbole x, mais le type
de sa valeur. Comparer avec :
..................................................................................................................................
..................................................................................................................................
s'abstenir. De sorte que x pointe vers un objet non simpli, assez complexe, dont
il est lgitime de demander le type :
..................................................................................................................................
> whattype(x) ;
..................................................................................................................................
La procdure whattype ne retourne pas le type d'un objet, mais un type qu'elle
essaie de dterminer au mieux parmi les types possibles pour l'objet en question.
En eet un type n'est autre qu'un ensemble d'objets Maple, et ces ensembles ne
sont pas en gnral disjoints. L'ensemble vide est en particulier un type, c'est le
type nothing. Aucun objet n'est du type nothing, pas mme le symbole nothing :
..................................................................................................................................
false
..................................................................................................................................
true
..................................................................................................................................
La procdure whattype pourrait donc rpondre anything pour tout objet, mais son
utilit ne serait pas vidente. On ne peut pas lui demander non plus de retourner le plus petit type contenant l'objet, car il existe toujours un type contenant
seulement cet lment. Par exemple l'objet sqrt(2) est l'unique lment du type
identical(sqrt(2)) :
..................................................................................................................................
true
false
..................................................................................................................................
> whattype(sqrt(2)) ;
..................................................................................................................................
Il faut une bonne vue pour voir que le type choisi est dsign par le symbole accent
circonexe ; si on veut en avoir le cur net :
..................................................................................................................................
true
..................................................................................................................................
Le symbole dsignant le type est exotique et doit donc tre encadr par des backquotes (accents graves) pour tre entr comme tel, sinon :
..................................................................................................................................
..................................................................................................................................
Chaque fois qu'un objet est structur, son codage commence par indiquer un
75
oprateur
dominant, et la procdure whattype retourne cet oprateur1 . Par exemple
2 est cod comme `^`(2, 1/2) = 2^(1/2) = 21/2 et l'oprateur matre est
l'exponentiation, ce qui explique la rponse de whattype
. De
true
..................................................................................................................................
> eval(Not) ;
> Not(anything) ;
Not
Not(anything)
..................................................................................................................................
alors que l'utilisateur naf attendrait plutt, compte tenu de ce qui a t expliqu page 75, que le dernier rsultat soit nothing. La mthode utilise par Maple
pour donner l'utilisateur la possibilit de manipuler les types est la suivante.
Des symboles (integer, boolean, symbol, . . .) sont rservs pour les types lmentaires (integer, boolean, symbol, . . .). D'autres types peuvent alors tre dcrits
l'aide d'expressions fonctionnelles citant un pseudo-constructeur et un ou plusieurs
types pseudo-arguments ; par exemple le descripteur Not(float) utilise le pseudoconstructeur Not et le pseudo-argument float. Le mcanisme est bien sr rcursif.
..................................................................................................................................
..................................................................................................................................
Quelquefois le pseudo-constructeur peut tre utilis sans argument, mais un argument implicite anything est alors suppos.
..................................................................................................................................
f alse
dismantle ; mais l'approximation donne ici sut pour ce qui nous concerne.
76
..................................................................................................................................
..................................................................................................................................
La procdure examine d'abord si l'objet considr est un entier, puis s'il est divisible par 3. Ceci fait, la notion d'objet divby3 a maintenant un sens dans l'environnement.
..................................................................................................................................
..................................................................................................................................
> radnormal(x) ;
4
..................................................................................................................................
dans les procdures qui savent tirer parti de la nature mathmatique du nombre .
3 Les considrations qui suivent sont dconseilles aux lecteurs fragiles aux troubles existentiels.
77
que |xn+k xn | < 2n si k > 0. Le thorme de Cauchy 4 assureque la suite (xn ) est
convergente et dnit donc un unique rel, sa limite. Le rel 2 peut par exemple
tre dni par :
..................................................................................................................................
..................................................................................................................................
..................................................................................................................................
satisfaisant les conditions requises ci-dessus pour une suite de Cauchy ; le rel
ainsi dni est entier mais ce fait n'admet aucune dmonstration. La preuve
d'existence d'une telle procdure n'est pas, ne peut pas tre, constructive ; pire,
aucune procdure ne peut tre identie comme telle ! Mais on est physiquement
certain que de telles procdures existent ; aussi certain qu'on sait qu'aprs avoir
ajout deux billes un sac qui en contenait deux, le sac contient quatre billes.
C'est un avatar du thorme d'incompltude de Gdel [2].
Vous pouvez par exemple tomber un jour sur une procdure de ce type qui
vous retourne pour chaque entier n que vous essayez une approximation xn vriant
|3 xn | 2n ; observant ceci, vous suspectez alors que le nombre rel limite x
ainsi dsign est en fait l'entier 3 ; vous cherchez donc une dmonstration que, quel
que soit l'entier n, le rsultat xn vrie cette ingalit, ce qui prouverait que le rel
limite est bien l'entier 3. Mais vous ne trouvez pas de telle dmonstration. dfaut,
vous essayez un grand nombre de nouvelles valeurs de n esprant enn trouver
le contre-exemple qui pourrait exister ce que vous aviez cru dans un premier
temps ; mais non, pour toutes ces nouvelles valeurs de n, l'ingalit |3 xn |
2n est dsesprment satisfaite ; utilisant ce rsultat qui semble dcidment
conrmer que le rel dni est entier, vous remettez en chantier la recherche d'une
dmonstration, que vous ne trouvez pas, etc. etc.
Quand vous serez un peu fatigu de ce travail sans n, invitablement vous
4 On
peut si on prfre considrer que ceci est une dnition de la notion de nombre rel.
78
suspecterez que vous tes en face d'un rel du troisime type, mais vous ne pourrez jamais le dmontrer non plus. . . L'exemple du nombre de Ramanujan vient
l'esprit, mais en fait il n'est pas de cette nature.
Le nombre de Ramanujan, e 163 , est assez instructif des dicults qui peuvent
tre rencontres quand on veut savoir si un nombre est entier ou pas. Aectons-le
au symbole r :
..................................................................................................................................
> r := exp(Pi*sqrt(163)) ;
r := e 163
..................................................................................................................................
> evalf(r) ;
.2625374126 1018
..................................................................................................................................
.26253741264076874443 1018
..................................................................................................................................
Il est un peu fatigant de compter les chires pour voir o la virgule est insre ;
un achage plus sophistiqu base d'impression formatte s'impose : puisque
20 chires exacts sont prvus et que 18 doivent se trouver avant la virgule,
l'achage de type %21.2f est le bon :
..................................................................................................................................
..................................................................................................................................
Mais peut-on avoir conance dans la partie dcimale ? Poussons un peu la prcision.
..................................................................................................................................
..................................................................................................................................
La question semble dcidment plus dlicate que prvu ! Il n'est certainement pas
possible que les derniers chires des deux rsultats prcdents soient exacts en
mme temps. . . Augmentons encore la prcision :
..................................................................................................................................
..................................................................................................................................
Il est clair maintenant que le nombre de Ramanujan n'est pas entier. On note au
passage que les deux derniers chires d'un rsultat ottant sont en gnral assez
douteux. Le thorme suivant permet de dterminer la nature arithmtique du
79
nombre de Ramanujan.
Il en
rsulte que le nombre de Ramanujan r est transcendant. En eet le nombre
= i 163 est algbrique : il est racine de l'quation 2 +163 = 0, et de plus il n'est
pas rationnel ; si le nombre = r tait entier,
il serait en particulier algbrique ; il
i 163
est aussi dirent de 0 et 1 et donc = r
serait transcendant. Calculons ce
dernier avec Maple :
..................................................................................................................................
> r^(I*sqrt(163)) ;
(e 163 )
I 163
> simplify(%) ;
1
..................................................................................................................................
qui n'est pas un nombre transcendant ! le nombre de Ramanujan est donc transcendant. Ramanujan avait devin il y a bien longtemps, sans Maple et sans ordinateur,
que son nombre, malgr sa taille imposante, tait non entier mais trs proche d'un
entier.
Error, fact expects its 1st argument, n, to be of type nonnegint, but received -1
..................................................................................................................................
analogue n'est disponible pour les variables des procdures, qu'elles soient locales5
ou globales.
La programmation rcursive rituelle de la fonction factorielle choue sous Windows pour n 530 pour cause de rcursivit trop profonde.
On voit aussi qu'on peut refuser l'achage d'un output en remplaant le terminateur ; (point-virgule) par : (deux-points) ; l'instruction est excute, mais
l'achage de l'objet retourn par l'valuateur n'est pas fait. On utilisera systmatiquement cette faon de faire pour la construction des procdures, o l'output est
en gnral de peu d'intrt.
1
..................................................................................................................................
13
..................................................................................................................................
Noter aussi que whattype ne rpondra pas rational pour le type d'un tel
nombre, mais seulement fraction :
..................................................................................................................................
> whattype(e30) ;
fraction
true
..................................................................................................................................
Curieusement les objets qui paraissent d'abord tre des fractions sont en fait
des produits :
5 Possible
sous Maple 6.
81
..................................................................................................................................
false
true
..................................................................................................................................
car le produit A/B est cod de faon interne (A1)*(B(-1)). La seule exception
notable cette remarque concerne le cas o A et B sont en fait des entiers, celui o
A/B est donc alors un objet rational.
integer
oat
..................................................................................................................................
Maple prvoit par dfaut une prcision de dix chires signicatifs pour les objets
float. On force l'valuation vers un ottant, partout o elle est possible, par la
procdure evalf.
..................................................................................................................................
> evalf(20^20/30^30) ;
> evalb(4. = 4) ;
> is(4. = 4) ;
.5092866261 1018
false
true
..................................................................................................................................
On voit ici une subtilit qui peut l'occasion tre importante ; la procdure d'valuation boolenne evalb est hard et compare en particulier les types des objets ;
la comparaison de l'entier 4 et du ottant 4. est donc ngative. Au contraire la
procdure is, dans le cas numrique, compare numriquement. Voir aussi :
..................................................................................................................................
x := ( 5 1) ( 5 + 1)
82
false, true
..................................................................................................................................
La procdure is est trs peu documente ; le listing source est disponible, mais trs
complexe. Sauf cas assez simples, son usage n'est pas trs clair et cette procdure
doit donc tre utilise avec beaucoup de prudence.
Pour obtenir un listing source, il faut d'abord modier un paramtre de l'interface appel verboseproc :
..................................................................................................................................
> interface(verboseproc = 2) ;
..................................................................................................................................
> eval(is) ;
proc(obj, prop )
local . . .
..................................................................................................................................
> eval(evalb) ;
..................................................................................................................................
2.7182818284590452354
..................................................................................................................................
Par dfaut, Maple prvoit des calculs avec 10 chires exacts, information qu'on
trouve dans la variable Digits :
..................................................................................................................................
> Digits ;
10
..................................................................................................................................
> Digits := 30 ;
Digits := 30
..................................................................................................................................
et dsormais tous les calculs ottants vont tre eectus avec la prcision demande.
83
..................................................................................................................................
> evalf(sqrt(3)) ;
1.73205080756887729352744634151
..................................................................................................................................
Une autre faon de demander qu'une valuation ottante soit eectue, consiste
prvoir des arguments ottants. Si Maple voit qu'une fonction a un argument
ottant, Maple en dduit logiquement que le contexte est calcul numrique et
continue dans le mme esprit, on dit qu'il y a contagion du type float. Comparer :
..................................................................................................................................
> Digits := 10 :
sin(1), sin(1.), sin(3/2), sin(1.5) ;
3
sin(1), .8414709848, sin( ), .9974949866
. . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .2. . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
Les utilisateurs sont souvent surpris sinon agacs quand Maple laisse une expression comme sin(1) sans valuation. Mais Maple prfre toujours garder la possibilit de mener ultrieurement des calculs exacts. Comparer les deux cas suivants :
..................................................................................................................................
..................................................................................................................................
Dans le premier cas les arguments sont gards exacts et Maple connat assez de
trigonomtrie pour conclure l'galit. Dans le second cas l'unique point dcimal
ajout a, par contagion, transform l'argument du premier sinus en une approximation ottante inexacte, d'o le rsultat. Plus simplement :
..................................................................................................................................
f alse
..................................................................................................................................
Conseil 19 Dans des calculs d'envergure, il est important d'avoir les ides
84
..................................................................................................................................
ce qui surprend un peu le mathmaticien, mais le type realcons est prvu avec une
smantique un peu plus prcise : on dit en mme temps que l'objet vis est une
constante.
..................................................................................................................................
a :=
( 2)
> type(a, realcons) ;
true
> evalf(a) ;
1.005154190
..................................................................................................................................
ex
dx
1+x
f alse
> evalf(b) ;
374.9536307
..................................................................................................................................
3.6 Alias.
Un alias est un symbole dclar synonyme d'un objet Maple. Le premier rexe la lecture de cette dnition consiste penser la notion de chanage, voir
Section 2.3.2 ; un chanage est en eet aussi un lien, install dans l'environnement,
entre un symbole et un objet Maple ; de sorte qu'une bonne lucidit va tre ncessaire pour bien comprendre la dirence entre les deux notions. Sans un eort
signicatif en ce sens, attendez-vous des dicults srieuses dans les situations
complexes.
Le sujet aurait mieux sa place comme satellite de ce qui avait t dit au sujet
de l'environnement, mais, strictement parlant, les alias ne sont pas indispensables,
de sorte qu'il est meilleur d'attendre qu'ils deviennent franchement utiles. C'est
le cas dans les deux sections suivantes, consacres aux nombres complexes et aux
nombres algbriques, et le sujet est donc maintenant l'ordre du jour.
Considrons donc qu'un alias est, comme un chanage, un lien entre symbole et
objet6 . Il est install par l'intermdiaire de la procdure alias. C'est une procdure
o chaque argument est un objet equation, autrement dit deux objets spars par
le signe = ; ces objets sont valus, et aprs valuation, le membre de gauche doit
tre un symbole, la source de l'alias dnir, le membre de droite est un objet
quelconque, le but de l'alias. Autant d'alias que d'quations seront construits. Dand
l'exemple qui suit, les deux membres de l'quation sont valuation triviale, et le
symbole source est donc alias_symbol, l'objet but est l'expression 1+x.
..................................................................................................................................
I, alias_symbol
..................................................................................................................................
Quand un nouvel alias est install, Maple retourne la suite des symboles aliass, y
compris le dernier ; dans l'environnement initial, seul le symbole I est alias. Il s'agit
maintenant de bien analyser la dirence fondamentale entre alias et chanage.
..................................................................................................................................
bounded_symbol := 1 + y
..................................................................................................................................
6 En
fait un alias peut admettre une source de type quelconque ; pour les usages les plus
frquents, la source est un symbole et, pour simplier, nous considrons seulement ce cas.
86
Ces exemples sont parfaitement articiels et ne gurent ici que dans un but
didactique. Le point cl est le suivant. On a expliqu Section 2.2.2 le modle ReadEval-Print de Maple. On a compris l'essentiel de la dirence entre chanage
et alias quand on a bien vu comment et pourquoi un chanage n'intervient que
pendant la phase Eval alors qu'un alias n'intervient que dans les phases Read et
Print.
Pendant la phase Read, Maple lit caractre par caractre le texte de l'instruction que vous lui proposez, et construit l'objet Maple, plus gnralement (cas
d'instructions d'aectation, conditionnelle, itrative. . .) l'instruction Maple que
vous voulez faire valuer. Si un symbole alias gure dans votre texte, ce symbole va tre systmatiquement remplac par l'objet correspondant. Pour mettre en
vidence ce fait, comparez soigneusement ce qui suit.
..................................................................................................................................
> has('alias_symbol', x) ;
true
> has('bounded_symbol', y) ;
f alse
..................................................................................................................................
L'analyse est la suivante. Le lecteur Maple a construit dans le premier cas l'objet
has('1+x', x), car il a vu la prsence du symbole alias_symbol et l'a remplac par
l'objet 1+x. Puis l'objet construit par le lecteur est pass l'valuateur. La procdure has est standard et les arguments sont valus avant d'tre utiliss, de sorte
que le premier argument dnitif est la somme 1+x : les quotes sont retirs par
l'valuation, voir Eval-10. Enn la procdure has travaille et voit qu'eectivement
le second argument x gure dans le premier 1+x, elle retourne donc true. Dans le
second cas, le symbole bounded_symbol n'est pas alias et le lecteur va donc passer l'valuateur l'objet has('bounded_symbol', y) ; rappelons que le lecteur n'est
pas concern par l'environnement. Quand l'valuateur travaille, le premier argument provisoire 'bounded_symbol' devient l'argument dnitif bounded_symbol o
ne gure pas le symbole y et la rponse est donc ngative.
Montrons maintenant que le mcanisme alias ne travaille pas pendant une
valuation. Il est assez compliqu de mettre ce fait en vidence, car il faut arriver
faire valuer le symbole alias sans le montrer parce qu'il serait aussitt remplac
par le lecteur par le but de l'alias ! Une faon d'y arriver consiste obtenir le
symbole par rsultat d'une procdure de construction. L'oprateur de construction
d'un symbole par concatnation, oprateur ., convient pour ce faire.
..................................................................................................................................
> i := 1 : sample.i ;
sample1
..................................................................................................................................
D'o la comparaison :
..................................................................................................................................
> has(alias_sym.bol, x) ;
f alse
> has(bounded_sym.bol, y) ;
true
..................................................................................................................................
87
Cette fois les objets passs l'valuateur sont exactement ceux que vous voyez,
car le symbole alias_symbol ne gure pas dans le texte entr. Le premier argument dnitif, construit par l'oprateur ., est le symbole alias_symbol, car ce
symbole n'est pas prsent dans l'environnement, et l'objet retourn par l'oprateur de concatnation est donc l'argument dnitif. Au contraire bounded_symbol
est prsent, de sorte que le premier argument dnitif dans ce cas est la valeur de
ce symbole, savoir 1+y. C'est une illustration du mcanisme de post-valuation,
cf. Eval-13 : le symbole retourn par l'oprateur de concatnation est son tour
valu. D'o les rponses respectivement ngative et positive.
On note ici que toute tentative de comprhension la va-vite du style avec
alias a value plus (ou moins) qu'avec l'aectation est en chec. Dans le premier
cas, c'tait le mcanisme alias qui valuait plus, dans le second cas c'tait le
contraire, mais de toute faon cette terminologie pifomtrique est impropre et doit
tre proscrite. Le bon point de vue consiste avoir les ides claires sur la phase de
travail de Maple o le lien symbole-objet est utilis.
Enn le mcanisme alias reprend du service dans la phase Print. Le plus
simple pour le mettre en vidence est ceci :
..................................................................................................................................
> 1 + x, 1 + y ;
alias_symbol, 1 + y
..................................................................................................................................
Maple recherche en eet systmatiquement dans les objets achs des composantes aliases, et le cas chant remplace ces occurenses par l'alias. Ici Maple a
vu la prsence de l'objet 1+x et l'a donc remplac dans l'achage par le symbole
alias_symbol. On voit donc que, contrairement aux chanages de l'environnement,
le lien alias est bidirectionnel alors que le lien chanage est orient. Ce point est
mis en vidence par :
..................................................................................................................................
..................................................................................................................................
> has([%], x) ;
true
..................................................................................................................................
Ici, il faut encadrer le rsultat suite entre crochets pour en faire une liste, sinon
.
les arguments passs has seraient incorrects ; voir
Rien n'interdit d'avoir la fois le mme lien entre symbole et objet, simultanment sous forme alias et chanage environnement. Compte tenu de la pr-valuation
des arguments de la procdure alias, ceci peut tre fait comme suit.
..................................................................................................................................
symb := 1 + x
88
I, alias_symb, symb
..................................................................................................................................
Selon les exemples donns prcdemment, on vrie la prsence simultane souhaite chanage et alias, par les instructions sotriques :
..................................................................................................................................
true, symb
..................................................................................................................................
Ce n'est pas un exercice de style sans motivation ; on verra que les calculs dans
les groupes de Galois, Chapitre
, sont grandement facilits par cette technique.
> x := 3+4*I ;
3 + 4I
> alias(I = I) ;
> x ;
3 + 4 1
> x ;
3 + 4I
..................................................................................................................................
Comme pour un symbole qu'on veut librer, la suppression d'un alias est conventionnellement demande par l'quation symb = symb si symb est le symbole source
dont on veut supprimer l'alias. Noter en particulier que les alias ne sont pas utiliss
pendant l'valuation des arguments de la procdure alias, sans quoi il serait trs
dicile le plus souvent d'atteindre le symbole dont on veut supprimer ou modier
l'alias ! Ceci a comme consquence un inconvnient quelquefois assez pervers :
89
> sqrt(-5) ;
..................................................................................................................................
> whattype(3+4*I) ;
+
..................................................................................................................................
L'oprateur dominant est en eet l'addition et whattype n'a pas de raison d'examiner les oprandes qui peuvent tre trs. . . complexes. Le type indiqu pour I
lui-mme est ;
..................................................................................................................................
> whattype(I) ;
..................................................................................................................................
Comme souvent, il est plus appropri de chercher si tel objet est de tel type :
..................................................................................................................................
true
Un objet est de type complexcons s'il est une constante complexe, donc sans symbole libre. Les rels sont en particulier des complexes :
..................................................................................................................................
true
..................................................................................................................................
1
2
1
5 I arctanh
5
5
5
5
5
> evalf(%) ;
1.404962947 .4304089412 I
..................................................................................................................................
Il arrive mme assez souvent que les utilisateurs soient surpris par le degr de
gnralit suppos par Maple ; en particulier Maple ne suppose pas par dfaut que
vos symboles sont valeurs relles. D'o l'aventure qui survient inexorablement
aux novices quand ils essaient de sparer parties relle et imaginaire d'un complexe.
L'examen de la documentation mne aux procdures Re et Im qui travaillent comme
on pense :
..................................................................................................................................
C'est le premier essai possible ; mais quelquefois celui qui vient l'esprit est le
suivant ; on cre un complexe abstrait
..................................................................................................................................
> z := x+I*y ;
z := x + Iy;
..................................................................................................................................
I(y), R(y)
x ,y
..................................................................................................................................
Les variables propos desquelles une ou des hypothses ont t faites sont signales
par un tilde suivant leur nom. Ce n'est pas le sujet de cette section, mais le contexte
est favorable pour signaler dans le mme registre :
91
..................................................................................................................................
> restart ;
> sqrt(x^2) ;
> simplify(%) ;
x2
csgn(x) x
..................................................................................................................................
..................................................................................................................................
La procdure evalc tente de prsenter son argument sous une forme xexpr +
I*yexpr.
..................................................................................................................................
> exp(I*Pi/10) ;
> evalc(%) ;
> evalc(exp(I*Pi/11)) ;
1
I
10
e
q
1
2
4
5+
5+I
1
1
5
4
4
1
1
) + I sin( )
11
11
..................................................................................................................................
cos(
Quand un objet est valu sous evalc, les symboles libres gurant dans l'objet
sont supposs rels et l'valuateur tient compte de cette hypothse momentane
pour sparer si c'est possible partie relle et imaginaire. Ceci permet assez souvent de se passer de la procdure assume quand les questions de sparations sont
trs localises. Exemples typiques aprs un restart ncessaire pour supprimer les
hypothses prcdemment installes par assume :
..................................................................................................................................
> restart ;
> Re(x+I*y) ; evalc(Re(x+I*y)) ;
<(x + Iy)
x
> Re(exp(x+I*y)) ; evalc(Re(exp(x+I*y))) ;
<(ex + Iy )
ex cos(y)
..................................................................................................................................
92
> P3 := X^3 + X + 1 ;
P 3 := X 3 + X + 1
> irreduc(P3) ;
true
..................................................................................................................................
Le corps K2 = Q[X]/(P 3), extension du corps K1 = Q, est donc mathmatiquement dni. Pour pouvoir y travailler commodment on procde dans l'espace de
travail Maple exactement comme dans l'espace de travail mathmatique. On crit
volontiers en mathmatiques que K2 = Q[] o est un nouveau nombre vriant 3 + + 1 = 0. Autrement dit K2 est obtenu partir de K1 par adjonction
d'un nouvel objet. Les lments de Q[] sont les polynmes a2 + b + c avec
a, b et c rationnels ; chaque tel polynme est considrer comme le reprsentant
canonique d'une classe d'quivalence de Q-polynmes modulo P 3 ; l'irrductibilit
de P 3 assure que K2 est bien un corps. En particulier est racine du polynme
P 3 ; le corps K2 contient donc au moins une racine de P 3 mais pour le moment
on ne sait pas s'il en contient d'autres.
Pour ajouter notre espace de travail Maple, on cre un alias.
..................................................................................................................................
I,
..................................................................................................................................
et dsormais est un objet comme un autre, un nombre algbrique, qui, strictement parlant, n'est rien d'autre que la classe d'quivalence de X dans le quotient
Q[X]/(P 3). Un calcul hors contexte ne donne rien de nouveau par rapport ce
qui tait prcdemment disponible :
..................................................................................................................................
> (1 + alpha)^6 ;
(1 + )6
93
> expand(%) ;
..................................................................................................................................
52 12 21
..................................................................................................................................
Ici le rsultat est simple, mais dans ce contexte les rsultats euves sont frquents
et il peut tre important pour la lisibilit d'crire le polynme rsultat ordonn :
..................................................................................................................................
52 21 12
..................................................................................................................................
> evala(RootOf(X^3+2*X+1)^3) ;
1 2 RootOf(_Z 3 + 2 _Z + 1)
> evala(RootOf(X^3+X+1)^3) ;
1
..................................................................................................................................
On voit que dans le deuxime cas, mme si on n'utilise pas l'alias disponible en
entre, Maple l'utilise si possible en sortie.
Une autre faon de voir que le polynme initial P 3 est irrductible, consiste
tenter de le factoriser.
..................................................................................................................................
> factor(P3) ;
X3 + X + 1
..................................................................................................................................
Dans le corps K1 = Q, le polynme P 3 n'a pas de racine. Par contre il a une racine
dans K2 = Q[], ce qui est mis en vidence comme suit :
..................................................................................................................................
(X 2 + X + 1 + 2 ) (X )
..................................................................................................................................
On voit qu'on dispose dans la procdure factor d'un argument optionnel complmentaire indiquant que la factorisation doit tre ralise dans une extension de Q,
dnie par l'intermdiaire d'un objet RootOf, adjoint Q.
..................................................................................................................................
true
..................................................................................................................................
> P2 := evala(P3/(X-alpha)) ;
P 2 := X 2 + X + 1 + 2
..................................................................................................................................
I, ,
..................................................................................................................................
0
..................................................................................................................................
(X ) (X + + ) (X )
..................................................................................................................................
L'achage est assez encombrant, mais on repre immdiatement l'occurence rpte d'un nouveau RootOf pour lequel on va aussi crer un alias ; on voit que
notre RootOf est en particulier le premier membre de l'quation qui est le premier
(unique) lment de la premire liste du rsultat ; notre alias peut donc tre cr
comme suit8 :
..................................................................................................................................
I, , ,
..................................................................................................................................
95
..................................................................................................................................
> %% ;
[[ = 2 + ], [ =
1
5
1
4 5
1
+ + 2 + 4 , = 2 4 ]]
qui est maintenant bien lisible. Que faut-il lire ? Que l'lment primitif choisi
par Maple est la combinaison = 2 + , et que les deux gnrateurs et
s'expriment comme polynmes simples l'aide de . Le polynme minimal de
est trs particulier ; c'est un polynme de degr 6 et pourtant son corps de dcomposition est aussi de degr 6, alors qu'un polynme de degr 6 choisi au hasard a
en gnral un corps de dcomposition de degr 720 sur Q. Extrayons ce polynme ;
la variable systme _Z est laide et on la remplace par X :
..................................................................................................................................
..................................................................................................................................
> irreduc(P6) ;
true
..................................................................................................................................
factor(P6, gamma)
1
..................................................................................................................................
On est tout prs de la thorie de Galois qu'on rexaminera plus tard dans ce
manuel ; disons seulement que le degr du corps de dcomposition d'un polynme
de degr infrieur 8 est directement accessible sous Maple comme suit :
..................................................................................................................................
> galois(P6)[4] ;
6
..................................................................................................................................
..................................................................................................................................
P (e2ik/8 ) = k ; 0 k 7.
Puisqu'il s'agit d'un problme trs classique d'interpolation polynmiale, une
procdure Maple est peut-tre toute prte pour un tel travail ? La recherche
Topic Search mne rapidement la procdure interp, trs simple d'utilisation.
L'exemple suivant sut pour en comprendre le fonctionnement.
..................................................................................................................................
..................................................................................................................................
..................................................................................................................................
Maple sait exprimer lmentairement les racines 8-imes de l'unit. Il ne reste plus
qu' utiliser ces donnes :
..................................................................................................................................
+ 12 . . .
1
1
1
1
1
1 1
1
((
2 + I 2 1)(
2 + I 2 I)(I
2 I 2)(
2 + I 2 1))
2
2
2
2
2
2
2
2
..................................................................................................................................
Le temps de calcul est trs bref, 1 seconde sur un PC moyen, mais le rsultat9 , dont
on n'a montr ici que le dbut de la premire ligne, est euve : l'auteur a compt
patiemment 379 crans de formules base de radicaux. Les tentatives rituelles
base de simplify et radnormal pour tenter de rduire le rsultat ne donnent rien,
de sorte que le rsultat est pratiquement inexploitable. On trouve ici une situation
typique o un calcul exact choue cause de sa trop grande complexit. Si le but du
calcul est le trac graphique obtenu page 102, des donnes ottantes sont toujours
susantes, et il est donc lgitime de se rabattre sur un calcul de type ottant. On
convertit donc nos racines de l'unit sous forme ottante et on applique le mme
calcul de polynme d'interpolation.
9 L'exprience
montre que l'ordre des termes achs est arbitraire d'une session l'autre.
97
..................................................................................................................................
..................................................................................................................................
Le polynme d'interpolation est cette fois visible d'un coup d'il ; de plus
les coecients sont remarquablement simples et laissent subodorer des proprits
arithmtiques souterraines dans le calcul d'interpolation en cours. Les coecients
du style 1.207106778 sont moins clairs, mais leur quasi rptition nous incite
lucider ce qui peut expliquer ces phnomnes. Une ide naturelle consiste alors
isoler le coecient de Z dans P ; on sait qu'il est gant et on ne l'ache pas.
..................................................................................................................................
> a1 := coeff(P, Z, 1) :
..................................................................................................................................
puis on normalise par rapport aux radicaux ce coecient isol. Cette fois la normalisation va rapidement au bout et donne :
..................................................................................................................................
1
1
1
I + I 2
. . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .2. . . . . . .2
. . . . . . . . . . . .2. . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
a1rn :=
..................................................................................................................................
Aux erreurs d'arrondi prs, les coecients sont bien les mmes. On peut faire le
mme travail pour les autres coecients, un par un, ce qui peut d'ailleurs tre
automatis : on a expliqu plus haut que les tentatives usuelles de simplication
chouent, mais il est maintenant clair qu'en traitant les coecients un par un, on
doit aboutir. On oriente normalement le calcul en ce sens comme suit, mais ne le
faites pas !
..................................................................................................................................
> P2 := collect(P, X) ;
..................................................................................................................................
Il semble en eet qu'un bug10 Maple soit ici : Maple reste sans rponse, les indicateurs Time et Bytes en bas de l'cran restent inactifs, et l'utilisateur ne peut
reprendre la main. Seule solution : abattre sa session de l'extrieur.
Ceci est assez troublant, et au lieu d'utiliser la procdure collect, on peut
chercher traiter soi-mme la gestion coecient par coecient.
10 Sous
98
..................................................................................................................................
Le but est-il atteint ? Si on en juge d'aprs le rsultat obtenu, oui ; ceci dit
le dernier calcul demande une quarantaine de secondes11 et compte tenu de la
simplicit du rsultat obtenu, il est trs tentant de chercher une mthode plus
simple permettant de court-circuiter les objets euves intermdiaires.
C'est le moment de penser que la solution rpute nave pour le problme
d'interpolation passe par une matrice de Vandermonde. Il s'agit en eet de trouver
des coecients i vriant les huit quations linaires :
7
X
j=0
I,
..................................................................................................................................
..................................................................................................................................
Maple ne semble pas savoir que 4 = 1, mais on peut lui souer d'exploiter ce
type de relation par application de la procdure evala explique page 94.
..................................................................................................................................
..................................................................................................................................
> with(linalg) :
..................................................................................................................................
99
..................................................................................................................................
1
1
1 2
1 3
vdm :=
1 1
1 2
10
12
12
15
18
10
12
14
21
14
12
15
18
21
..................................................................................................................................
On sait comment tenir compte de 4 = 1 ; une valuation explicite du symbole vdm est ici ncessaire pour atteindre la matrice pointe par le symbole
vdm : l'exception signale pour les valeurs procdures en Eval-16 intervient aussi
pour les valeurs matricielles ; voir Eval. D'o l'appel trange mais invitable
evala(eval(.... On cache le rsultat, vident mais encombrant.
..................................................................................................................................
..................................................................................................................................
1
1
8
8
1
1
1
8
4 (1 + 4 )
1
8
1 1
8 2
1
8
1
4 1 + 4
1
8
1
1
8
1 1
8 2
1 1
8 2
1
4 1 + 4
1
8
1 1
8 2
1
8
1
8
1 1
8 2
1
4 1 + 4
1
8
1
8
1
8
1
1
4 (1 + 4 )
1
8
1 1
8 2
1
8
1
4 1 + 4
1
1
1
8
8
8
1
1
1
1 1
8
4 (1 + 4 )
8 2
1
8
1
8
1 1
8 2
1
4 1 + 4
1
8
1 1
8 2
1 1
8 2
1
1
4 (1 + 4 )
1
8
1
1
1 1
1
8
8 2
8
1 1
1
1
1
8 2
4 (1 + 4 )
8
1
8
1
1
4 (1 + 4 )
1 1
8 2
1
4 1 + 4
1
8
1 1
8 2
1
8
4 1 + 4
1 1
8 2
1
1
4 (1 + 4 )
1
8
1
4 1 + 4
1 1
8 2
1
1
4 (1 + 4 )
..................................................................................................................................
100
..................................................................................................................................
1
1
3
8 8
1
1
8
8
1
1
8 8
ivdm :=
1
1
8
8
1
1 3
8
8
1
1 2
8
8
1
1
8
8
1
8
1 2
8
1
8
1 2
8
1
8
1 2
8
1
8
1 2
1
8
1
8
1 2
8
1
3
8
1
8
1
8
1
2
8
1 3
1
8
1
8
1
8
1
8
1
8
1
8
1
8
1
1
8
1
8
1 3
8
1
2
8
1
8
1
8
1 3
8
1 2
8
1
8
1 2
8
1
8
1
2
8
1
8
1 2
8
1
8
1
2
8
1
8
1
8
1 2
8
1 3
8
1
8
1
8
1
2
8
1
3
8
..................................................................................................................................
..................................................................................................................................
aprs quoi on vrie que le produit de notre candidat inverse par la matrice inverser est 8 fois la matrice identit ; la procdure evalm value l'expression matricielle
et l'appel de evala demande de tenir compte de 4 = 1 ; enn la procdure
iszero examine si la matrice obtenue est nulle.
L'inversion si facile est due aux proprits particulires de l'ensemble des racines de l'unit : on a retrouv les proprits les plus simples de la transformation
de Fourier discrte, voir par exemple [5]. Un autre point de vue peut aussi tre
considr ; examinons le conditionnement de la matrice inverser. Comparer :
..................................................................................................................................
..................................................................................................................................
:= [ 27 , 12 + 12 3 + 12 2 + 21 , 12 + 12 2 , 12 + 21 12 2 + 21 3 , 12 ,
21 12 3 + 12 2 21 , 12 12 2 , 12 12 21 2 21 3 ]
..................................................................................................................................
Notre polynme d'interpolation est cette fois obtenu par un calcul qui n'a pos
aucune dicult particulire : aucun rsultat intermdiaire ingrable l'cran,
1.3 seconde de temps CPU.
On voulait obtenir une courbe ferme du plan complexe joignant les huit points
rels de ydata. Il sut de tracer l'image du cercle unit par le polynme exactP.
Il faut mieux utiliser la procdure complexplot du package plots :
..................................................................................................................................
..................................................................................................................................
..................................................................................................................................
102
..................................................................................................................................
..................................................................................................................................
..................................................................................................................................
..................................................................................................................................
On voit ainsi la racine 0, conrme aussi par la forme exacte du polynme d'interpolation, et les six autres racines manifestement de module 1. Pour conrmer
ce point de vue, on peut commencer par pousser la prcision ; le calcul avec 30
chires signicatifs ne prend pratiquement pas plus de temps et conrme notre
conjecture. Si au lieu de prendre huit points sur le cercle unit du plan complexe, on
en prend un nombre pair quelconque, le mme rsultat est observ ; et un rsultat
analogue est aussi constat dans le cas impair. Il reste obtenir une dmonstration
mathmatique gnrale de ce fait, mais c'est une autre histoire13
13 Indications.
103
polynme est coecients rels ; il a la racine 0 et les autres racines sont les ` 6= k , nk1 ; on
en dduit sa forme Pn,k = XQn,k o le polynme Qn,k est coecients symtriques ; de plus le
polynme Qn,k est strictement positif sur l'axe rel. Donc toute combinaison coecients positifs
des polynmes Pn,k (n x) va avoir les mmes proprits : une racine 0 et les autres racines
sur le cercle unit du plan complexe. Or le polynme du texte se dduit d'une telle combinaison
par une manipulation simple. Une tude analogue aboutit dans le cas n impair. La symtrie
assez rudimentaire l'origine de notre phnomne est ainsi lucide ; par exemple le polynme
d'interpolation o les valeurs successives sur les 10 racines 10-imes de l'unit sont 2, 4, 1, 3, 5,
-5, -3, -1, -4 et -2 va prsenter la mme proprit : la courbe image du cercle unit va passer huit
fois par l'origine :
104
Chapitre 4
Listes, ensembles, suites et tables.
4.1 Introduction.
Ce chapitre est consacr des objets Maple qui, selon le contexte, pourraient
tre appels composs, ou itratifs, bien qu'aucun de ces qualicatifs ne soit sufsant pour dnir notre sujet. En langage C++, une paire d'accolades {. . ., . . .}
regroupe plusieurs instructions pour en produire une seule, qu'on appelle alors
instruction compose. Dans le mme esprit, si obj1, obj2, . . ., objn sont des objets
Maple, alors :
[obj1, obj2, ..., objn]
dsigne un objet compos, appel liste, ou encore objet list. Mais d'autres objets
comme par exemple l'objet function :
operator(operand1, ..., operandn)
est aussi en un sens un objet compos, mais qui n'est pourtant ni une liste, ni
un ensemble, ni une suite, ni une table. On verra toutefois que la suite des
oprandes operand1, ..., operandn est bien une suite au sens prcis donn par
Maple cette notion, et de telles suites d'oprandes (ou d'arguments) seront donc
considres dans ce chapitre, notamment Section 4.4.
Un autre point de vue est considrer ; l'instruction C++ :
..................................................................................................................................
..................................................................................................................................
excute 10 fois la mme instruction, ceci prs que l'environnement est dirent
chaque itration : la valeur de i est modie. Dans le mme esprit l'instruction
Maple :
..................................................................................................................................
105
..................................................................................................................................
construit une liste o les lments sont tous de mme nature, un cube d'entier,
mais l'entier en question est variable d'un entier l'autre. Un tel objet peut donc
tre appel naturellement un objet itratif, mais d'autres listes ont au contraire
des lments trs dirents deux deux et ne peuvent pas raisonnablement entrer
dans cette catgorie.
Dcidons d'appeler listes, ensembles, suites et tables des objets multiples, pourquoi pas. Les objets multiples Maple sont donc de type list, set, exprseq ou table.
Le type table admet le sous-type array, lequel admet son tour les sous-types
matrix et vector ; les deux derniers types sont bien entendus ddis d'abord au
calcul matriciel.
Le type exprseq est vraiment l'un des ingrdients essentiels de Maple. Les lispeurs reconnatront dans les objets de type exprseq, absolument partout dans
Maple, la version adapte des listes de Lisp ; rappelons que Lisp est une contraction de List Processing. De mme que les cellules cons sont les particules lmentaires des objets Lisp, l'ingrdient de base pour la construction des listes Lisp, la
structure de type exprseq est le noyau de la structuration des objets Maple. C'est
peu dire que la comprhension des objets de ce type est la cl indispensable pour
entrer dans la confrrie des initis Maple.
Warning 21 Les quatre types exprseq (suite), list (liste), set (ensemble) et
table (table) sont disjoints deux deux. Une suite ne peut pas tre ni une liste,
ni un ensemble, ni une table. De mme pour toutes les autres combinaisons deux
deux.
Rien n'empche un lment de suite d'tre une liste, un ensemble ou une table ;
de mme pour les lments des listes, ensembles et tables. Par contre un lment
de suite, liste ou ensemble ne peut jamais tre une suite. Un lment de table peut
lui tre absolument de tout type ; il peut en particulier tre une suite.
Les relations d'appartenance possibles sont runies dans ce tableau.
exprseq
list
set
table
exprseq
Non
Oui
Oui
Oui
list
Non
Oui
Oui
Oui
set
Non
Oui
Oui
Oui
table
Oui
Oui
Oui
Oui
106
> seq4 := a, b, c, d ;
list4 := [a, b, c, d] ;
set4 := {a, b, c, d} ;
table4 := table([1=a, 2=b, 3=c, 4=d]) ;
seq4 := a, b, c, d
list4 := [a, b, c, d]
set4 := {a, b, c, d}
table4 := table([
1=a
2=b
3=c
4=d
])
..................................................................................................................................
Nos objets multiples ont tous quatre lments. Pour construire une suite, les
lments constituants sont spars par virgule. De mme pour liste et ensemble,
ceci prs que pour une liste il faut prvoir en plus crochets ouvrant et fermant, et
pour un ensemble, accolades ouvrante et fermante. Pour une table, on peut utiliser
le constructeur table avec comme argument une liste d'quations cl = objet.
On voit qu'une liste (resp. ensemble) n'est rien d'autre, typographiquement,
qu'une suite encadre de crochets (resp. accolades). Ceci n'est pas une convention
pour les reprsentations externes ; il en est essentiellement de mme en mmoire.
Avant de dtailler ce point, il faut d'abord expliquer que la virgule ne doit pas
tre comprise comme un procd syntaxique ; c'est vritablement l'oprateur inx
n-aire permettant de construire une suite. Comparer dans ce registre les deux
instructions :
..................................................................................................................................
> a + b + c ;
a , b , c ;
a+b+c
a, b, c
..................................................................................................................................
o l'analogie est parfaite, et ce n'est pas une analogie, c'est une ralit. L'auteur
suit le plus souvent en entre l'usage typographique : pas de blanc avant la virgule,
un blanc aprs ; mais ceci n'est qu'un usage, sans aucune importance pour le lecteur
Maple.
Donc une expression avec n oprandes spars par n 1 virgules est lue comme
une suite de n lments. Ceci n'a de sens que si n 2. En particulier la notion de
suite un lment n'a pas de sens ! Par contre la suite vide existe et est accessible
en particulier par l'intermdiaire du symbole NULL, protg, qui pointe vers cette
suite, invisible, comme on le voit ci-dessous.
107
..................................................................................................................................
> whattype(seq4) ;
exprseq
> wrong_seq1 := a ;
wrong_seq1 := a
> whattype(wrong_seq1) ;
symbol
right_seq0 :=
> whattype(right_seq0)
exprseq
..................................................................................................................................
On a expliqu qu'une liste (resp. ensemble ) n'est autre qu'une suite encadre
par crochets (resp. accolades). C'est si vrai que les liste et ensemble points par
list4 et set4 auraient pu aussi bien tre construits comme suit :
..................................................................................................................................
..................................................................................................................................
et en mmoire il en est de mme ; un objet list est une entte indiquant qu'il s'agit
d'une liste et un unique pointeur vers un objet exprseq, moins que la liste ait un
seul lment, auquel cas le pointeur pointe directement vers cet lment, car une
suite un lment n'a pas de sens1 .
Donc listes et ensembles ne sont en quelque sorte que des objets satellites de
suites. Une liste n'est autre qu'une suite avec un chapeau indiquant qu'il s'agit en
fait d'une liste, de mme pour un ensemble. Il y a pourtant une dirence entre les
constructeurs de listes et d'ensembles ; une liste n'est vraiment rien d'autre qu'une
suite avec un chapeau, un ensemble aussi, mais le constructeur d'ensemble va
en plus vrier que les objets constituants sont dirents deux deux. Le cas
chant, les objets doublons sont carts. De plus l'ordre des objets achs est
sans importance pour un ensemble alors qu'il l'est pour une liste. En fait Maple
trie pour un ensemble selon les adresses machine. Comparer :
..................................................................................................................................
> seq6 := a, z, e, r, a, z ;
> list6 := [seq6] ;
seq6 := a, z, e, r, a, z
list6 := [a, z, e, r, a, z]
set4 := {a, r, z, e}
..................................................................................................................................
108
..................................................................................................................................
L'objet function est construit puis aect au symbole function3 ; quand on demande le type de la valeur de ce symbole, la procdure whattype rpond justement
function. On obtient le nombre d'oprandes de la valeur du symbole function3
l'aide de la procdure nops :
..................................................................................................................................
> nops(function3) ;
3
..................................................................................................................................
Moyennant quoi on sait que la valeur de function3 est un objet avec trois
oprandes. On peut demander par exemple le deuxime oprande :
..................................................................................................................................
bcd2
..................................................................................................................................
abc
..................................................................................................................................
On a ainsi un procd trs gnral et trs simple pour analyser tout objet.
Considrons par exemple cet objet appel une intgrale inerte ; c'est une intgrale o le choix de l'oprateur Int commenant par une majuscule, au lieu de
l'oprateur d'intgration usuel int commenant par une minuscule, demande explicitement Maple de ne pas valuer l'intgrale et donc de la garder telle quelle.
On verra plus tard de nombreuses circonstances o de tels objets inertes sont
utiles, voire indispensables.
109
..................................................................................................................................
II :=
x3 dx
1
..................................................................................................................................
> nops(II) ;
Int
x3
On voit qu'en fait le format interne correspond exactement ce qui avait t entr
pour la cration de l'objet.
Le choix d'une intgrale inerte pour cette illustration n'est pas innocent ; l'intgrale inerte, par principe, n'est pas value. Comparer le mme exercice avec la
procdure int ordinaire, celle qui cherche eectuer l'intgration :
..................................................................................................................................
fraction
15
. . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .4. . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
Il faut rester toujours vigilant ce propos ; malgr leur parfum systme, les procdures nops et op sont standard et valuent leurs arguments avant de les utiliser,
source permanente de piges dans les debuggings vreux.
Les procdures nops et op fonctionnent en particulier pour les listes. Considrons cette liste biscornue :
110
..................................................................................................................................
Z 2
list4 := 27, x2 + y 2 , ,
x3 dx
1
> nops(list4) ;
4
..................................................................................................................................
Notre liste, dans la terminologie Maple, est donc un objet quatre oprandes,
correspondant ce qui est appel d'habitude les lments de la liste. On peut
demander l'oprande 4 :
..................................................................................................................................
x3 dx
1
..................................................................................................................................
et l'oprande 0 :
..................................................................................................................................
list
..................................................................................................................................
x = 1..2
..................................................................................................................................
ou si on prfre :
..................................................................................................................................
x = 1..2
..................................................................................................................................
Noter que les indices successifs sont alors lire de gauche droite et doivent tre
les constituants d'une liste. Et ainsi de suite :
..................................................................................................................................
x
..................................................................................................................................
..................................................................................................................................
111
..................................................................................................................................
f(g)
x3 dx
> op(1, %) ;
x3
> op(0, %) ;
..................................................................................................................................
x3 dx
x
..................................................................................................................................
On peut encore appeler la procdure op avec un seul argument, l'objet analyser ; dfaut de prcision sur l'oprande souhait, la procdure retourne alors la
suite des oprandes, oprateur exclu.
..................................................................................................................................
> op(list4) ;
Z
2
27, x + y , ,
x3 dx
1
..................................................................................................................................
Autrement dit on a ralis la conversion objet list objet exprseq, et ceci est
la seule faon d'y parvenir. Cette conversion est souvent indispensable et l'exemple
qui prcde doit donc tre bien compris. Un exemple typique d'application consiste
chercher l'lment maximum d'une liste ; la procdure max est disponible et tout
le monde espre d'abord pouvoir l'utiliser ainsi :
..................................................................................................................................
..................................................................................................................................
112
Il faut en eet ncessairement retirer les crochets, c'est--dire convertir liste vers
suite.
..................................................................................................................................
> max(op(list5)) ;
46
..................................................................................................................................
Plus explicitement :
..................................................................................................................................
46
..................................................................................................................................
x2 + y 2 ,
x2 + y 2 ,
list, 27, x2 + y 2 , ,
x3 dx
1
..................................................................................................................................
113
..................................................................................................................................
..................................................................................................................................
On voit que chaque symbole pointant vers une suite a t remplac par la suite en
question ; autrement dit l'oprateur virgule est en fait un oprateur de concatnation entre suites, o, cas le plus frquent, tout oprande qui n'est pas une suite
est remplac par la suite constitue de cet unique lment. Ceci semble contredire
le warning expliquant qu'un lment de suite ne peut pas tre une suite, mais justement, l'valuateur tient compte de notre warning et en quelque sorte enlve
les parenthses implicites que vous croyez peut-tre voir ; les concepteurs de Maple
auraient aussi bien pu dcider ici que la valeur du symbole seq16 est une suite
trois lments o le premier et le troisime auraient t des suites, mais ce n'est
pas le choix qui a t fait ; ils ont dcid que si un argument de l'oprateur virgule
est une suite, alors la suite argument est concatne aux suites adjacentes. C'est
souvent commode, mais ncessite d'tre bien compris. Aucun parenthsage, mme
intensif, ne changera ceci :
..................................................................................................................................
..................................................................................................................................
comparer avec :
..................................................................................................................................
..................................................................................................................................
> max(2, 4, 3) ;
4
..................................................................................................................................
6
..................................................................................................................................
ce qui dans certains contextes peut tre assez commode. Cette technique est par
114
exemple bien utile quand vous avez dcid une fois pour toutes d'utiliser les procdures de trac graphique avec les options couleur, paisseur du trac et type de
trac ci-dessous :
..................................................................................................................................
..................................................................................................................................
On ne montre pas ce trac, hors sujet ici. Mais l'usage rpt des mmes options
peut tre abrg par la dnition de la suite de trois quations aecte au symbole
my_options :
..................................................................................................................................
..................................................................................................................................
..................................................................................................................................
Ce qui semble tre l'unique argument my_options est dvelopp en trois arguments, chacun d'eux tant un objet equation.
On est maintenant enn capable de comprendre ce qu'on tait bien en peine
d'expliquer page 19. Reprenons l'expression qui tait value :
..................................................................................................................................
..................................................................................................................................
..................................................................................................................................
Autrement dit les parenthses redondantes, fautives pour un profane, ici sont parfaitement lgales et n'ont provoqu aucune erreur. Mais la fonction intgrer,
compte tenu de la priorit suprieure de la division sur l'addition, est la fonction :
1+
x
1 + x2 + x4
et l'intgrale est donc divergente ; alors que l'utilisateur souhaitait en fait intgrer :
1+x
1 + x2 + x4
115
Warning 22 Les procdures d'analyse op, nops et type ne peuvent tre utilises
pour analyser les suites.
Reprenons par exemple notre suite seq456, et tentons d'en dterminer le nombre
d'oprandes :
..................................................................................................................................
> seq456 ;
4, 5, 6
> nops(seq456) ;
Error, wrong number (or type) of parameters in function nops
..................................................................................................................................
alors que le profane attend videmment le rsultat 3. Mais rchissez aux consquences de ce qui a t expliqu plus haut ; ce que l'utilisateur croit voir comme
un unique argument est transform par le mcanisme de prvaluation Eval-14 en
une suite trois lments 4, 5 et 6. De sorte que notre appel quivaut :
..................................................................................................................................
> nops(4, 5, 6) ;
..................................................................................................................................
qui provoque l'erreur constate, puisque la procdure nops ne doit tre appele
qu'avec un seul argument. On aurait prfr ici que notre argument volue en un
unique argument suite qui aurait donc pu tre trait de faon cohrente par la
procdure nops, mais on perdrait alors la possibilit montre plus haut de runir
en un seul argument my_options les trois arguments de la procdure plot qu'on
ne souhaite pas rpter chaque appel. Comme toujours, l'essentiel est de savoir
lucider le cas chant comment le moteur Maple va en dnitive fonctionner dans
tel ou tel cas.
Le mme phnomne va engendrer des anomalies invitables avec les procdures
op et type.
..................................................................................................................................
> op(seq456) ;
..................................................................................................................................
Plus vicieux :
..................................................................................................................................
> op(seq12) ;
2
..................................................................................................................................
car :
116
..................................................................................................................................
> op(0..1, 2) ;
integer, 2
..................................................................................................................................
..................................................................................................................................
> whattype(seq456) ;
exprseq
..................................................................................................................................
..................................................................................................................................
117
..................................................................................................................................
..................................................................................................................................
..................................................................................................................................
La conversion inverse peut aussi tre obtenue de l'une ou l'autre faon. Par contre
la procdure convert ne sait pas raliser les conversions vers une suite ou d'une
suite. Le second cas est logique puisqu'on buterait nouveau sur le problme
de l'argument suite dvelopp le plus souvent en plus d'un argument. On peut
supposer que pour respecter une symtrie tentante, les concepteurs Maple n'ont
pas souhait proposer la conversion inverse, qui ne poserait en fait aucun problme.
..................................................................................................................................
..................................................................................................................................
car une procdure peut parfaitement retourner une suite, ce qui est souvent commode. Il est frquent que des procdures Maple de porte assez gnrale peuvent
tre tendues par l'utilisateur pour couvrir tel ou tel cas non prvu par les concepteurs Maple. On avait dj vu cette technique pour la procdure type page 77.
Le cas de la procdure convert ici est analogue. L'utilisateur peut alors dnir
une procdure `mapleproc/othercase` o mapleproc est une procdure Maple prdnie, et othercase est un symbole expliquant que si tel argument d'un appel
de mapleproc est othercase, alors l'appel doit tre trait comme expliqu dans
le corps de la procdure introduite. Pour le cas ajout exprseq de convert, on a
simplement expliqu qu'il fallait appliquer l'objet convertir la procdure op.
Noter que la prsence du slash / dans le nom de la procdure impose les backquotes encadrant le symbole, sous peine d'erreur. Il faut comprendre que le nom
de la nouvelle procdure est un peu exotique pour dissuader l'utilisateur d'utiliser
directement cette procdure ; c'est en fait faisable, mais sans intrt :
118
..................................................................................................................................
> `convert/exprseq`(list2) ;
..................................................................................................................................
list4 := [a, b, c, d]
..................................................................................................................................
Le mme rsultat est obtenu l'aide d'une notation indexe, sensiblement plus
lisible :
..................................................................................................................................
> list4[2] ;
> list4[2..3] ;
[b, c]
par la n ;
..................................................................................................................................
> list4[-3] ;
> list4[-3..3] ;
[b, c]
..................................................................................................................................
Ce qui est illustr ici sur les listes s'applique exactement de la mme faon pour
les ensembles. Mais, et ceci est important, contrairement la procdure op qui est
inutilisable pour les suites, l'extraction indexe d'lments de suite travaille comme
on le souhaite.
..................................................................................................................................
> seq4 := a, b, c, d ;
seq4 := a, b, c, d
> seq4[2] ;
b
> seq4[-3..3] ;
b, c
..................................................................................................................................
> list4[2] := bb ;
> list4[-2] := cc ;
> list4 ;
list42 := bb
list42 := cc
[a, bb, cc, d]
..................................................................................................................................
Ceci n'est utilisable que pour les listes, ne fonctionne donc pas pour les ensembles
et les suites. Ne pas essayer non plus la modication de sous-liste.
..................................................................................................................................
..................................................................................................................................
Il faut toutefois tre assez mant dans ces instructions de modication de liste.
Compte tenu de ce qui vient d'tre expliqu, le pige suivant fonctionne presque
coup sr :
..................................................................................................................................
..................................................................................................................................
Il peut se faire qu'au cours d'une session, on ait prouv la ncessit d'isoler le
deuxime lment, qui est aussi une liste (cf. Warning-21) :
120
..................................................................................................................................
..................................................................................................................................
puis on peut avoir une raison de modier par exemple le second lment de cette
liste :
..................................................................................................................................
pair22 := bbb
[b, bbb]
..................................................................................................................................
> list32 ;
..................................................................................................................................
et on voit que la valeur de list32, elle, est inchange ! Dans un exercice d'tudiant
comme ici, cette tranget est identiable, mais si un tel vnement se produit
pendant la mise au point d'un programme complexe, le bug rsultant peut tre
extrmement dicile expliquer ! Une analyse soigneuse mais dlicate coups de
procdures systme addressof, pointto et disassemble, montre que la modication
de l'lment pair2[2] modie aussi la valeur, plus prcisment l'adresse de la valeur
de pair2 ; une nouvelle liste est cre, avec les pointeurs ad hoc, mais comme au
contraire rien n'est chang pour la valeur de list32, la liste valeur de ce dernier
symbole est inchange !
Comparer avec :
..................................................................................................................................
..................................................................................................................................
Cette fois c'est la sous-liste repre par pair2 qui n'est pas modie.
Warning 23 La modication d'un terme de liste ne modie que la liste explicitement indique comme devant tre modie ; les listes apparemment partages
ne sont pas modies.
Noter aussi que les deux instructions suivantes sont parfaitement quivalentes,
pour la lecture de l'lment de liste comme pour sa modication :
121
..................................................................................................................................
bbb, bbb
..................................................................................................................................
..................................................................................................................................
..................................................................................................................................
elles sont dconseilles ds qu'elles sont frquentes ou concernent des listes relativement longues ; elles sont de toute faon exclues si la longueur de liste est > 100.
Le cas chant, il faut prfrer, selon les circonstances, un type de donne vector
ou table.
Si la liste volutive est de longueur constante, la solution vecteur est la plus
ecace :
..................................................................................................................................
..................................................................................................................................
Si la liste est de longueur variable mais avec longueur maximale connue d'avance,
la mme solution est utilisable, avec des conventions appropries pour marquer les
cases en fait vides :
122
..................................................................................................................................
..................................................................................................................................
etc. Voir Section 4.9.1 pour les dtails, en particulier pour comprendre pourquoi
le vecteur est ach comme une liste, mais n'est pourtant en aucune faon une
liste. Pour des situations beaucoup plus imprvisibles, il faut utiliser des tables,
voir Section 4.7.
expr := a2 + b2 + c2
a2 , b2 , c2
a2 + bb3 + c2
..................................................................................................................................
> expr ;
a2 + b2 + c2
..................................................................................................................................
..................................................................................................................................
Une certaine cohrence peut tre ncessaire dans la substitution, sous peine d'erreur :
123
..................................................................................................................................
..................................................................................................................................
puisqu'un terme d'une somme ne peut pas tre une suite ; ici le parenthsage de
la suite membre de droite de l'quation premier argument vitait toute confusion
sur la nature des arguments ; comparer avec :
..................................................................................................................................
..................................................................................................................................
..................................................................................................................................
Dans certains contextes, ceci pourrait avoir un sens, par exemple dans un contexte
vectoriel.
Revenons au sujet principal de cette section, savoir les listes et ensembles. La
procdure subsop peut tre utilise pour des manipulations conduisant intercaler
ou supprimer un terme de liste ou d'ensemble, car cette fois, l'objet substituer
peut tre une suite avec un nombre quelconque d'lments.
..................................................................................................................................
list4 := [a, b, c, d]
> subsop(2 = (b, bb, bbb), list4) ;
[a, b, bb, bbb, c, d]
> subsop(2 = NULL, list4) ;
[a, c, d]
..................................................................................................................................
> restart ;
..................................................................................................................................
L'importance des suites dans la structure des objets Maple commence s'imposer.
Il est donc important de disposer de constructeurs commodes pour crer des objets o les suites sont des constituants essentiels ; l'oprateur virgule permet de
124
construire les suites lment par lment, mais il serait fort pnible de construire
ainsi par exemple la suite des entiers de 1 1000. La procdure seq est idale pour
ce faire. Elle utilise une variable pilote, un symbole2 . La procdure seq ncessite
deux arguments ; le premier est un terme gnrique, un objet Maple quelconque o
gure le plus souvent la variable pilote ; le second argument est un objet equation
dont le membre de gauche doit tre la variable pilote, et le membre de droite est le
plus souvent un range, c'est--dire deux expressions qui seront values, spares
par l'oprateur ... Par exemple pour construire la suite des cubes des entiers de
10 20 on peut procder comme suit :
..................................................................................................................................
..................................................................................................................................
Dans cet appel de la procdure seq, la variable pilote est le symbole i ; le terme
gnrique est l'objet Maple i3 ; le range dcrivant le domaine de variation de la
variable pilote est l'objet 10..20. Si le deuxime membre de l'quation deuxime
argument n'est pas un objet range, il est interprt d'une faon un peu dirente ;
dans un tel cas, la variable pilote va parcourir la suite des oprandes de ce second
membre. Exemple typique :
..................................................................................................................................
..................................................................................................................................
..................................................................................................................................
On voit que les deux appels sont analogues ceci prs que pour la procdure seq,
le nom de procdure est prxe, prcdant les deux arguments parenthss, alors
que pour la procdure $, l'oprateur est inx, c'est--dire insr entre les deux
oprandes. C'est vrai, mais il y a une autre dirence beaucoup plus importante,
invisible sur notre exemple simple : le mcanisme d'valuation des arguments est
compltement dirent.
L'argument expr1 est d'abord valu ; soit expr11 l'objet rsultat de l'valuation ;
l'argument expr2 est ensuite valu et le rsultat de cette valuation doit tre une
quation symb = n1..n2 o symb est un symbole, n1 et n2 sont deux entiers. Alors
l'expression expr11 est rvalue dans un contexte o le symbole symb pointe successivement vers les entiers n1, n1+1, . . ., n2. Les (n2-n1+1) rsultats successifs
sont les composants de la suite rsultat.
Construisons une procdure espion pour mettre en vidence les direntes
2 Ou
plus gnralement un nom ; autrement dit une variable indice peut aussi tre utilise,
mais ceci n'est que trs rarement utilis.
125
..................................................................................................................................
La procdure spy, quand elle est appele, ache un message signalant l'appel,
permettant aussi de voir quel est l'argument dnitif 3 qui est pass ; de plus la
procdure retourne seulement cet argument.
..................................................................................................................................
> spy('message') ;
Evaluating spy(message)
message
..................................................................................................................................
spy(spy(i^2))
spy(i)
spy(2)
spy(3)
spy(4)
spy(9)
4, 9
..................................................................................................................................
..................................................................................................................................
..................................................................................................................................
page 61.
126
..................................................................................................................................
Si par contre le second argument est une quation, la procdure seq value d'abord
son second membre, puis vrie que le premier est un symbole4 , sinon erreur :
..................................................................................................................................
..................................................................................................................................
false
..................................................................................................................................
true
..................................................................................................................................
Comme spy(i) est valu, l'argument dnitif est cette fois le symbole i qui est
bien un objet name ! L'exprience suivante ne peut tre que :
..................................................................................................................................
spy(2)
spy(3)
spy(spy(i^2))
spy(spy(i^2))
spy(i2 ), spy(i2 )
..................................................................................................................................
Encore une surprise, mais facile expliquer. Une fois que le second argument de seq
est valu, le premier est donc maintenant, et maintenant seulement, valu deux
fois, une fois dans un environnement o [i 2], une autre fois avec [i 3].
Mais puisque l'unique occurence du symbole i est entre quotes, ces valeurs de i
sont inutilises. L'argument dnitif de spy est l'expression spy(i2), qui ne sera
plus rvalue, d'o le rsultat sous forme de deux exemplaires de cette expression,
un pour chaque valeur de i demande. La dernire exprience est donc :
4 Plus
127
..................................................................................................................................
4, 9
..................................................................................................................................
expr2 est d'abord valu, soit expr22 l'objet retourn par l'valuateur ; le domaine
que doit parcourir la variable pilote symb est la suite des oprandes de expr22,
moins que cet objet soit un objet range auquel cas le domaine sera l'ensemble
des entiers dcrit par ce range. Ensuite l'objet expr1 est valu autant de fois que
ncessaire dans un environnement o le symbole symb pointe successivement vers
les dirents lments du domaine dduit de expr22. Le rsultat de l'valuation
sera la suite des rsultats d'valuation obtenus.
Conseil 27 D'une faon gnrale, la procdure seq est sensiblement plus adapte la construction des suites que l'oprateur $.
> rand(1..100)() ;
82
..................................................................................................................................
end
71
..................................................................................................................................
Pour une fois, on a montr le rsultat procdure5 pour mettre en vidence que la
5 Habituellement
128
Ce n'est pas du tout le rsultat souhait ! On voit ici que le luxe de dtails prcdemment donns dans cette section est loin d'tre superu. L'expression rnd100()
est d'abord value, choisit donc un nombre alatoire, ici 64 ; c'est l'objet not
expr11 dans Eval-25. Puis le deuxime oprande de l'expression $ est trait. Le
rsultat de la premire valuation, donc l'entier 64, est alors valu autant de fois
que ncessaire, donc 10 fois, dans un environnement o le symbole i pointe vers
1, puis vers 2, etc. Mais quel que soit l'environnement, le rsultat de l'valuation
de 64 est 64, d'o notre rsultat. Comparer avec ce qui est obtenu naturellement
avec la procdure seq :
..................................................................................................................................
Car cette fois le terme gnrique n'est valu qu'une fois pour chacune des valeurs
de i souhaites, valeurs qui ne jouent d'ailleurs aucun rle en elles-mmes. On
obtiendrait un rsultat analogue avec l'oprateur $ en interdisant la premire
valuation :
..................................................................................................................................
..................................................................................................................................
> a $ 5 ;
a, a, a, a, a
..................................................................................................................................
> 'rnd100()' $ 10 ;
> $ 5..10 ;
5, 6, 7, 8, 9, 10
..................................................................................................................................
129
1
2
3
On avait expliqu page 58 que l'instruction itrative for laisse le symbole i pointant
vers 4, d'o l'erreur dans l'instruction $ car la variable pilote y est value, alors
qu'au contraire l'appel de seq produit le rsultat escompt, car la variable pilote
n'y est jamais value. Ceci fonctionne :
..................................................................................................................................
mais c'est dtestable et propice bien des erreurs dans des situations plus complexes.
4.7 Tables.
La structure d'une table est assez dirente de ce qui a t expliqu pour les
suites, listes et ensembles. Dans le cas le plus gnral il s'agit en langage informatique d'un chier accs direct ; les articles sont des objets Maple quelconques, et
chaque article est accessible par une cl, un autre objet Maple lui aussi quelconque.
D'habitude, on appelle plutt indice ce qui est de fait une cl d'accs. Exemple
articiel :
..................................................................................................................................
..................................................................................................................................
Cette table a quatre articles (entries en jargon Maple), savoir les symboles a, b,
c et d. Chacun est accessible par sa cl (indice ), respectivement 1, 2, 3 et 4. Noter
que, contrairement ce qui est frquemment prvu dans les systmes de traitement
de chiers, la cl n'est pas une partie de l'article : les objets correspondants, article
et cl, sont disjoints, conceptuellement et aussi en machine.
Pour voir l'intgralit par exemple d'une liste qui serait pointe par le symbole
list3, il sut d'valuer le symbole list3 :
130
..................................................................................................................................
..................................................................................................................................
> table4 ;
table4
..................................................................................................................................
> eval(table4) ;
table([
1=a
2=b
3=c
4=d
])
..................................................................................................................................
> table4[2] ;
b
..................................................................................................................................
Il est lgal de citer une cl inexistante, auquel cas l'objet retourn est aussi un
objet index, type indexed :
131
..................................................................................................................................
> table4[55] ;
table455
true
..................................................................................................................................
Ceci fonctionne mme si l'oprateur n'value pas vers une table. Exemple articiel
pour expliquer le mcanisme :
..................................................................................................................................
> a := b ;
a := b
> a[a+4] ;
bb+4
> eval(b) ;
b
..................................................................................................................................
[a, b, c, d]
> list4[55] ;
Error, invalid subscript selector
..................................................................................................................................
On verra cependant que pour les tableaux, et donc en particulier pour les matrices
et les vecteurs, il est ncessaire de choisir la cration du tableau l'ensemble
des indices valides ; si un indice non valide est ensuite utilis, il entrane alors
logiquement une erreur. Ce point sera rediscut Section
.
132
..................................................................................................................................
> table4[3] := cc ;
table43 := cc
> eval(table4) ;
table([
1=a
2=b
3 = cc
4=d
])
..................................................................................................................................
> table4[3] ;
cc
..................................................................................................................................
..................................................................................................................................
Le symbole pointant notre table n'a pas chang, mais notre table a maintenant
5 lments ; l'article ajout est un symbole exotique, cause du caractre espace y gurant, et a ncessit les backquotes d'encadrement. Les nouvelles cls
ajoutes peuvent tre des objets Maple quelconques, idem pour les articles ajouts.
..................................................................................................................................
table455 := 5 &+ 11
..................................................................................................................................
Ici l'article ajout est une expression utilisant un oprateur inx non prdni ;
voir ce sujet la page de documentation intitule neutral.
Rien n'empche un article d'tre une suite :
..................................................................................................................................
> table4[x^2+y^2] := 1, 2, 3 ;
table4 2
:= 1, 2, 3
x + y2
..................................................................................................................................
..................................................................................................................................
Notre table est maintenant un objet auquel on serait bien en peine de donner
un sens raisonnable, mais ceci est sans importance pour Maple.
133
..................................................................................................................................
> eval(table4) ;
table([
x2 + y 2 = (1, 2, 3)
1=a
2=b
3 = cc
4=d
5 = fth element
55 = 5 &+ 11
(1, 2, 3) = {4, 5, 6, 7}
])
> table4[table4[y^2+x^2]] ;
{4, 5, 6, 7}
..................................................................................................................................
Bref, on voit que cls et articles peuvent tre des objets absolument quelconques,
et que les oprations usuelles de comparaison sont utilises pour identication ; en
particulier la rfrence de cl x2+y2 est synonyme de y2+x2.
table43 := table43
> assigned(table4[3]) ;
f alse
..................................................................................................................................
..................................................................................................................................
134
..................................................................................................................................
..................................................................................................................................
n := 3
a3 := 9
..................................................................................................................................
a4 := 444
444
Autrement dit, comme il l'avait dj t observ page 71, il n'y a pas d'valuation
au niveau suprieur dans le membre de gauche d'une instruction d'aectation, par
contre toute valuation un niveau infrieur, typiquement d'un indice, est eectue
pour dterminer quel est l'objet source du chanage installer ou modier.
Moyennant quoi vous pouvez comprendre l'exemple articiel suivant.
135
..................................................................................................................................
..................................................................................................................................
Il a fallu en eet quoter le symbole n en indice pour empcher son valuation an
de crer un lment d'indice n.
Dans le mme registre la libration d'un lment de table indice calcul va
poser problme. Supposons qu'on veuille librer l'lment de la table a dont l'indice
est la valeur de n. Ceci ne fonctionne pas :
..................................................................................................................................
a1 := 11
..................................................................................................................................
a1 := an
> a[1] ;
Error, too many levels of recursion
> eval(a[1], 1) ;
an
..................................................................................................................................
car on voit qu'on a cette fois trop empch l'valuation du terme de droite de
l'aectation ; ce n'est donc pas une auto-aectation qui est demande, de sorte
que Maple installe un chanage de a[1] vers a[n]. Provoquant ainsi quand on demande la valeur de a[1] une erreur amusante, consquence curieuse du mcanisme
de post-valuation, voir la rgle Eval-13 : la valeur de a[1] est a[n], oui, mais
n a pour valeur 1, donc l'valuateur obtient a[1], oui, mais a[1] a pour valeur
a[n], etc. Comme toujours, eval(..., 1) permet de demander une seule phase
d'valuation.
Et on voit qu'on est en panne pour demander l'auto-aectation souhaite !
Il faut en fait utiliser ici unassign ; on semble pourtant buter a priori sur les
mmes dicults. En particulier unassign(a[n]) va provoquer la mme erreur de
rcursisivit indnie :
136
..................................................................................................................................
> unassign(a[n]) ;
..................................................................................................................................
> eval(a[1], 1) ;
an
> unassign('a[n]') ;
> assigned(a[1]) ;
false
..................................................................................................................................
On voit que chaque cl, chaque article, est encadr entre crochets. Cette notation
assez lourde pour le rsultat est ncessaire pour lever l'ambigut qui pourrait
rsulter du Warning-21 : un lement de table, contrairement ce qui a t expliqu
pour les suites, listes et ensembles, peut tre une suite. Un indice de table peut aussi
tre une suite, auquel cas il devient essentiellement un multi-indice. Procdons aux
expriences rituelles pour examiner ces points.
6 Par
137
..................................................................................................................................
> a[1,2,3] := e ;
> a[f] := 4, 5, 6 ;
a1, 2, 3 := e
af := 4, 5, 6
On voit que sans les crochets dlimitant les multi-indices ou les lments suites,
on serait incapable d'interprter correctement les rsultats.
Dans le mme ordre d'ides, si on initialise une table avec des quations index
= entry, quand un indice est multiple, il doit tre parenths, pour lever le mme
genre d'ambigut.
..................................................................................................................................
..................................................................................................................................
Ici la liste a trois arguments dont deux ne sont pas des quations ; Maple dcide
donc l'aectation automatique des cls ; en particulier l'lment de cl 2 est l'quation 2 = 3 ; la concidence cl et premier membre de l'article est considrer
comme fortuite. Comparer avec les trois autres cas complmentaires.
..................................................................................................................................
..................................................................................................................................
Rien n'empche dans une table que certains indices soient multiples et d'autres
non, comme il l'avait dj t constat plus haut quand on examinait les rsultats
de la procdure indices.
138
> 1, 2 = 3, 4, 5 ;
1, 2 = 3, 4, 5
> 1, 2 = 3, (4, 5) ;
1, 2 = 3, 4, 5
4.8 Tableaux.
Les tableaux sont des tables particulires. Elles ont deux particularits :
1. L'ensemble des indices possibles pour leurs lments est dni une fois pour
toutes la cration du tableau ;
2. L'ensemble des indices possibles doit tre un produit cartsien d'intervalles
d'entiers :
[i1 . .j1 ] . . . [id . .jd ].
L'entier d est la dimension du tableau ; c'est un entier strictement positif.
Chaque indice est donc une suite d'entiers k1, ..., kd qu'on considre habituellement plutt comme un multi-indice ; mais en plusieurs circonstances, le seul
point de vue qui, strictement parlant, soit correct est selui-ci : l'unique indice est
une suite de d entiers.
Soit par exemple crer un tableau o la suite d'indices possible est le produit
[0. .4] [0. .4]. La procdure array peut tre utilise comme suit, et le tableau
139
m5 := array(0..4, 0..4, [ ])
..................................................................................................................................
Le tableau tant ainsi cr, ses lments peuvent maintenant tre aects, modis
ou supprims comme pour les tables, la condition expresse de ne citer qu'un indice
autoris, donc ici une suite de deux entiers du domaine 0..4. On peut par exemple
souhaiter installer dans m5[i,j] le produit modulo 5 des deux indices i et j, pour
obtenir la table de multiplication des entiers modulo 5 :
..................................................................................................................................
..................................................................................................................................
Aucun achage n'apparat l'cran ; ceci est d au fait que deux instructions for
sont embotes, et Maple juge que la profondeur de travail est alors trop importante
pour justier un achage qui risquerait d'tre un peu envahissant7 . La table m5
peut maintenant tre utilise pour obtenir un produit modulo 5 particulier.
..................................................................................................................................
> m5[2,4] ;
3
..................................................................................................................................
m6 := array(0..5, 0..5, [ ])
> for i from 0 to 4 do
for j from 0 to 4 do
m6[i, j] := (i * j) mod 6
od
od ;
..................................................................................................................................
0, m63,5
..................................................................................................................................
Mais toute tentative de citer un indice illgal sera sanctionne par un message
d'erreur assez clair.
7 Ce
point peut tre modi par l'utilisateur l'aide de la variable printlevel, voir la page
de documentation correspondante.
140
..................................................................................................................................
> m6[3, 6] ;
..................................................................................................................................
La notion d'indice illgal peut d'ailleurs tre assez subtile ; examinez ceci :
..................................................................................................................................
m63,t
> t := 4 : expr ;
0
> t := 6 : expr ;
Error, 2nd index, 6, larger than upper array bound 5
..................................................................................................................................
Le bon point de vue est le suivant : l'indice t peut tre ou non lgal selon
sa valeur, et dans le doute, Maple accepte l'indice. Si par la suite, on aecte au
symbole t la valeur 4 (lgale) ou 6 (illgale), l'valuation de expr est correcte ou
non.
4.8.1 Cration-Initialisation.
On peut initialiser directement tout ou partie des lments d'un tableau la
cration en prvoyant en plus une liste d'initialisation. Soit crer un tableau des
cubes des entiers compris entre 10 et 20 :
..................................................................................................................................
..................................................................................................................................
On voit ici que le mcanisme permettant de crer facilement, l'aide de la procdure seq, une suite d'lments itrative permet une initialisation confortable et
lisible. On peut critiquer le choix du symbole pluriel cubes, l'origine de l'appel
cubes[15], incohrent, puisqu'on ne demande qu'un seul cube ! mais si on choisit le
singulier, c'est la dsignation de la table elle-mme avec un singulier qui est alors
critiquable. Le perfectionniste en choix de symboles peut demander :
..................................................................................................................................
cube := cubes
> cube[16] ;
4096
..................................................................................................................................
Le profane peut penser ici que l'aectation du symbole cubes au symbole cube a
transmis aussi de faon souterraine la table sous-jacente valeur de cubes, comme
semble l'indiquer l'valuation qui suit. Cette interprtation est incorrecte ; quand
Maple lit l'expression valuer, il trouve une expression indexe, o, avant de faire
travailler le mcanisme de lecture de table, il value l'expression racine, ici cube ;
il trouve le symbole cubes et c'est donc partir de ce symbole qu'il cherchera
l'lment de table demand. D'une certaine faon, l'expression cube[16] est une
expression deux arguments, le premier le symbole cube, le second l'entier 16 ;
141
cubes := cubes
> cube[16] ;
cubes16
..................................................................................................................................
C'est ici un cas trs curieux qui semble contredire ce qui avait t expliqu page 53.
Dans l'instruction d'aectation cubes := cubes, l'valuation du second membre
est implicite et la valeur du symbole cubes tant une table, c'est seulement le symbole cubes qui est retourn, cause de la rgle Eval-16. Ensuite, l'aectation de
ce symbole lui-mme est interprte par Maple comme une demande de libration du symbole, voir page 53. Donc ici le symbole cubes est libr. Comme cube
chane toujours vers cubes, l'valuation de cube[16] provoque l'valuation de cube
vers cubes, mais puisque cette fois le symbole est libre, le mcanisme d'valuation
triviale s'applique et l'expression cubes[16] est en dnitive retourne.
On rediscutera ces questions quand on examinera les problmes assez subtils lis
aux changes de valeurs entre procdures et monde extrieur. Notez ds prsent
que des bugs subtils et trs coriaces lucider en sont souvent la consquence si
on ne procde pas de faon prcise en la matire.
Pour en terminer avec l'initialisation des tableaux, il faut aussi signaler que si
un tableau a une dimension multiple, il faut l'initialiser avec une liste de listes de
listes. . . avec la profondeur ad hoc.
..................................................................................................................................
..................................................................................................................................
4.9.1 Vecteurs.
Un vecteur est un tableau de dimension 1 o l'ensemble des indices est un range
1..n pour un entier positif n :
142
..................................................................................................................................
..................................................................................................................................
Les formes internes des deux objets construits sont pratiquement les mmes ; pour
A, l'indice varie de 0 2, alors que pour V il varie de 1 3. Mais ceci sut faire
de la valeur de V un vecteur, alors que la valeur de A n'est pas un vecteur :
..................................................................................................................................
..................................................................................................................................
Le lecteur (trs-trs) attentif doit ici tre surpris qu'on n'ait pas prfr :
..................................................................................................................................
..................................................................................................................................
car en principe une valuation explicite est ncessaire pour atteindre les valeurs
tableaux ; oui, mais la procdure type applique elle-mme l'valuation explicite au
premier argument si le type dsign au second demande une telle valuation pour
atteindre l'un de ses lments, ce qui nous dispense dans ce cas, et dans ce cas
seulement, de l'application de la procdure eval. Comparer avec :
..................................................................................................................................
..................................................................................................................................
o cette fois, puisque le type propos est symbol, seule une valuation implicite
est eectue !
Un vecteur est ach comme une liste mais n'est en aucune faon une liste :
..................................................................................................................................
> L := [4,5,6] ;
[4, 5, 6]
> type(L, list), type(L, symbol), type(L, vector),
type(V, list), type(eval(V), list) ;
true, f alse, f alse, f alse, f alse
..................................................................................................................................
Cette fois, pour une liste, mme l'valuation implicite du symbole L a retourn
la liste, et c'est pourquoi type(L, symbol) rpond ngativement ; l'valuation implicite ou explicite de V ne donne pas une liste, elle retourne respectivement un
symbole ou un vecteur.
143
4.9.2 Matrices.
La situation est trs analogue pour les matrices. Une matrice est un tableau de
dimension 2 dont les domaines de variation des indices commencent par 1.
..................................................................................................................................
..................................................................................................................................
De ces trois tableaux du mme style, seul le deuxime est une matrice.
..................................................................................................................................
..................................................................................................................................
1 2
M := 4 5
7 8
3
6
9
..................................................................................................................................
1 2
T2 :=
3 4
..................................................................................................................................
T2 est une matrice et est ache comme telle, alors que le domaine de variation
du premier indice de T1 exclut que T1 soit une matrice ; l'achage de T1 est donc
8 Voir
144
> with(linalg)
[BlockDiagonal, GramSchmidt, . . .
... ... ...
vecpotent, vectdim, vector, wronskian]
..................................................................................................................................
On n'a pas montr ici la liste complte des 114 procdures constituant ce
package. Tous les grands sujets classiques du calcul matriciel y sont traits. Par
exemple le dterminant de notre matrice M est nul :
..................................................................................................................................
> det(M) ;
0
..................................................................................................................................
Cette matrice est donc singulire, mais quel est son rang ?
..................................................................................................................................
> rank(M) ;
2
..................................................................................................................................
> K := kernel(M) ;
K := {[1, 2, 1])}
..................................................................................................................................
Sceptique ? Il faut alors valuer le produit de la matrice M par le vecteur qui vient
d'tre montr ; pour extraire ce vecteur de l'ensemble de vecteurs constituant la
base du noyau, ici rduite un lment, on peut utiliser l'indexation [1] ; un calcul
matriciel doit tre eectu sous evalm et l'oprateur de multiplication matricielle
est &*.
..................................................................................................................................
[0, 0, 0]
..................................................................................................................................
Ce calcul trs simple montre qu'on peut travailler interactivement avec des donnes matricielles quelconques. On en verra de nombreux exemples, voir notamment
. On avait dj vu un exemple relativement sophistiqu page 99 et
les chapitres
suivantes propos de problmes d'interpolation et de matrices de Vandermonde.
-o-o-o-o-o-o-
145
Chapitre 5
Programmation.
5.1 Introduction.
Maple n'est pas seulement un systme de calcul formel ; c'est aussi un langage
de programmation. Il est de ce point de vue thoriquement quivalent tous les
autres langages, bien que, comme chacun sait, selon le contexte, tel langage est
commode ou au contraire dlicat utiliser.
Le point de vue vident ce propos des concepteurs de Maple tait, et reste,
le suivant. Le contexte calcul symbolique est relativement dlicat, et pour viter
toute surcharge de complexit, un langage de programmation qu'on peut qualier
de rustique a t adopt.
Il a en particulier l'avantage d'tre facile apprendre, car conceptuellement
simple tout en tant logiquement bien quilibr. Sa faiblesse rapidement perue
comme la plus vidente est dans le typage des objets en gnral, des variables en
particulier. Avec une situation manifestement un peu dsquilibre de ce point de
vue : d'une part, d'innombrables types prdnis sont disponibles, et l'utilisateur a
de grandes facilits pour en crer de nouveaux sa guise. Mais il n'est pas possible
de dclarer les variables locales1 de procdures, ou mme les variables globales.
Ceci donne un style de programmation gnralement assez sauvage, proche de la
programmation en Lisp des premiers temps, o il arrive souvent de voir par erreur
une variable prvue pour localiser une matrice recevoir une. . . intgrale comme
valeur sans que Maple signale quoi que ce soit ! La procdure ASSERT permet de
mettre en uvre quelques prcautions dans ce registre, mais le plus souvent assez
rudimentaires.
146
if
condition 1
then
elif
instruction 1,1 ;
... ... ;
instruction 1,n1
condition 2
then
elif
elif
instruction 2,1 ;
... ... ;
instruction 2,n2
... ...
... ...
condition k
then
else
;
instruction k,1 ;
... ... ;
instruction k,nk
instruction k+1,1 ;
... ... ;
instruction k+1,nk+1
Il est rare et surtout franchement dconseill d'utiliser le maximum de gnralit ach ici ! Presque toujours, un minimum de rexion sur le sujet trait permet
de se dispenser des instructions conditionnelles multiples branches, de plus en
gnral assez peu lisibles. Ceci dit, qui peut le plus peut le moins et inversement
toute limitation sur le degr de gnralit montr ici, commun presque tous les
langages de programmation, serait malcommode dans tel ou tel cas particulier.
Seule relative originalit de Maple : la possibilit automatique d'insrer dans
chaque branche un nombre arbitraire d'instructions. Avec un inconvnient : cette
possibilit ncessite un indicateur de fermeture, fi en n d'instruction, ou bien un
sparateur, elif ou else indiquant le passage la branche suivante. Mais ceci a
dispens les concepteurs de Maple de prvoir un format d'instruction compose,
comparable au {. . . . . .} de C. Il rsulte de ceci que la faute d'criture consistant
oublier le fi terminal est trs frquente, et surtout n'est pas dtectable en place,
puisque le point-virgule suivant indique que la branche de then ou else continue.
Si ceci se produit dans le texte d'une procdure, la faute n'est le plus souvent dtectable qu'au end terminal, situation qui laisse l'utilisateur dans le vide chercher
147
5.2.1 if then .
C'est le cas le plus simple. Il intervient trs frquemment en dbut de procdure
pour traiter un ou plusieurs cas particuliers, permettant de dvier la procdure sur
un autre cas. Considrons par exemple l'exercice d'tudiant consistant mettre en
place une procdure de calcul numrique du logarithme de base 10, celle fournie
par le systme tant suppose en panne.
Un algorithme trs commode et de plus assez ecace pour ce faire consiste
n'utiliser que les quatre oprations classiques. Comme c'est souvent le cas, on a
intrt tre un peu plus gnral et installer un algorithme capable de calculer
(, , ) = + log(), pour > 0, le cas du logarithme seul tant le cas
particulier = 0 et = 1. Cette organisation permet en eet de reporter par
oprations lmentaires le logarithme vers jusqu' ce que la prcision souhaite
soit atteinte ; cette prcision est dnie par un paramtre , par exemple donn
comme = 1010 . On procde de faon itrative alors comme suit :
1. Si = 1, alors + log() = ;
2. Si < 1, alors + log() = log(1/) ;
3. Si 10, alors + log() = + + log(/10) ;
4. Si les conditions prcdentes ne sont pas satisfaites, c'est que 1 < < 10 et
donc 0 < log() < 1 ; dans ces conditions, si est non nul et si |/| < ,
l'exigence sur la prcision relative est satisfaite en se contentant de ;
5. Sinon on utilise + log() = + (/2) log( 2 ).
Il est facile de voir que l'volution de cet algorithme fait tendre / vers 0,
et la quatrime condition termine donc l'algorithme. La traduction en Maple, uniquement coups de if then s'crit alors :
148
..................................................................................................................................
..................................................................................................................................
..................................................................................................................................
..................................................................................................................................
> mylog10(2) ;
.3010299956
..................................................................................................................................
> log[10](2.);
.3010299957
..................................................................................................................................
Des tests faciles mener utiliser la procdure time permettent de constater que notre procdure est aussi ecace que la procdure Maple d'origine. Mais
la procdure Maple traite aussi le cas du logarithme complexe, non couvert par la
ntre. Cette dernire peut facilement tre adapte pour traiter d'autres bases de
logarithmes, et pour atteindre des prcisions suprieures, en jouant sur les variables
epsilon et Digits.
149
false
..................................................................................................................................
true
..................................................................................................................................
..................................................................................................................................
Comme usage un tout petit peu moins trivial de if then else , observons que la procdure mylog10 aurait pu tre termine d'une faon que beaucoup
prfrent :
..................................................................................................................................
..................................................................................................................................
bien que les deux mthodes soient ici parfaitement quivalentes. Cette quivalence
est due un phnomne particulier qu'il faut bien avoir identi : ici la prsence
d'une instruction RETURN dans une branche implique que de toute faon la procdure
est interrompue, que la condition teste comparaison avec soit satisfaite
ou non.
Pour montrer une situation dirente considrons le problme n/2 ou 3n + 1.
Soit n un entier positif quelconque. On applique de faon itrative le processus
suivant : si n est pair, on le divise par 2, sinon on le remplace par 3n + 1. On veut
une procdure qui retourne le nombre d'tapes ncessaires pour atteindre 1. Il est
conjectur que ce nombre est toujours dni, autrement dit que le processus dcrit
nit par atteindre 1, mais cette conjecture, trs ancienne, reste non dmontre
quand ces lignes sont crites. Version utilisant if then else :
150
..................................................................................................................................
2076
..................................................................................................................................
La procdure nsteps est vraiment programme comme on pense. Seule coquetterie, l'usage du mme nom pour la procdure et pour la variable locale compteur ;
certains n'aiment pas ce style, d'autres trouvent au contraire commode de dsigner ainsi implicitement quelle est la variable cl de la procdure. Noter aussi
la ncessit d'une variable locale nn initialise l'argument n, car il n'est pas possible sous Maple de modier cet argument, moins d'utiliser une technique qu'on
examinera en temps utile, page
, mais en fait ici inapproprie.
Comparer la version suivante o on a jou utiliser seulement la version
if then de l'instruction conditionnelle :
..................................................................................................................................
..................................................................................................................................
151
..................................................................................................................................
..................................................................................................................................
5.2.3 if elif . . .
La procdure phi qui nous a servi pour le calcul du logarithme de base 10 est
le plus souvent crite par les programmeurs :
..................................................................................................................................
..................................................................................................................................
5.3.1 do.
Encore appel do forever, car utilise directement sans prambule, cette instruction est indniment rpte ; elle ne peut alors tre interrompue que par une
instruction break ou RETURN, ou encore, plus piteusement, par un click sur le bouton
. Pour montrer un usage plausible de ce do, transformons nos procdures
stop :
mylog10 et phi (cf. pages 149 et 152) de la forme rcursive prcdemment utilise vers une forme itrative, un peu plus technique, mais indispensable en haute
prcision. Une seule procdure va maintenant sure.
152
..................................................................................................................................
..................................................................................................................................
> a := 2 ; b := 3 ;
a := 2
b := 3
tmp := 2
a := 3
b := 2
..................................................................................................................................
> a, b := b, a ; a, b ;
a, b := 2, 3
2, 3
..................................................................................................................................
> a, b := 2, 3 ;
a, b := 2, 3
> a, b := [b, assign('a' = b)][1], a ;
a, b := 3, 3
..................................................................................................................................
..................................................................................................................................
..................................................................................................................................
En eet le compteur est incrment par dfaut d'une unit chaque tour il
faut dire chaque itration de sorte que la clause for gre automatiquement
la progression de la variable FP que la plupart des programmeurs appelleraient
simplement i. Si pour une raison qui nous chappe, le cahier des charges demande
la premire puissance paire satisfaisant la mme condition, il sut d'utiliser la
sous-clause by :
154
..................................................................................................................................
..................................................................................................................................
Il serait bien sr plus rentable, dans le cas o chaque micro-seconde serait prcieuse,
de calculer une fois pour toutes le carr de a. Mais la terminaison elle-mme peut
tre simultanment gre par une clause while, ce qui donne un style beaucoup
plus compact.
..................................................................................................................................
..................................................................................................................................
Il se pourrait aussi qu'on craigne un temps de calcul trop long si a tait trop
proche de 1 et b trop grand ; on voudrait donc limiter tout prix 1000 le nombre
d'itrations.
..................................................................................................................................
..................................................................................................................................
..................................................................................................................................
..................................................................................................................................
Il arrive aussi qu'une clause while suse elle seule. Par exemple si, dans notre
procdure FirstPower, on est intress seulement par la valeur de la puissance et
non par l'exposant, on peut l'crire :
..................................................................................................................................
..................................................................................................................................
1
2
4
..................................................................................................................................
Il n'est pas dicile de dmontrer qu'on peut toujours se passer de ces instructions,
ceci dit il est frquent que leur usage facilite l'criture et amliore la lisibilit des
programmes itratifs un peu compliqus.
5.4 Tris.
La mthode standard pour vrier que l'essentiel est compris en programmation
conditionnelle et itrative consiste programmer les algorithmes lmentaires de
156
tri ; ils ncessitent en eet du programmeur une gymnastique instructive. Considrons par exemple l'un des tris les plus simples, le tri par insertion. On range les
objets trier les uns aprs les autres, insrant chaque objet la bonne place, qu'il
faut donc dterminer par rapport aux objets dj rangs. La liste des objets tris
augmente donc rgulirement, et les objets au-del de l'objet insrer doivent tre
dplacs pour laisser une place au nouveau venu. Plusieurs solutions techniques
sont possibles qu'il est intressant de comparer.
Mais avant de trier, il faut un objet raisonnable trier. Dans les exercices de
tri, ce sont classiquement des listes d'entiers. Soit donc construire une liste de 20
entiers alatoires compris entre 1 et 1000. On construit d'abord une procdure
de gnration, qu'on essaie par exemple cinq fois.
..................................................................................................................................
..................................................................................................................................
Pour avoir les ides plus claires, on va commencer par trier en crant un nouvel
objet, une liste qu'il faut initialiser la bonne longueur, en la remplissant par
exemple par des zros, comme suit.
..................................................................................................................................
..................................................................................................................................
157
> insertion1(list1) ;
[86, 86, 87, 161, 164, 199, 308, 350, 410, 458, 462, 467, 539, 656, 675, 710, 769, 917, 922, 974]
..................................................................................................................................
..................................................................................................................................
..................................................................................................................................
158
Un dfaut d'une autre nature est assez important. Ici, pour un exercice d'tudiant, il est secondaire, mais pour un vrai tri sur de grands ensembles, il aurait de
srieux inconvnients. On observe que list1[i] est utilis pour chaque comparaison, lecture dans une liste bien plus coteuse que le laisse penser le texte list1[i],
si court. Alors que cet objet aurait pu tre lu une seule fois et rutilis ensuite ; il
faut pour ce faire une nouvelle variable qu'on appelle fllw (following).
..................................................................................................................................
..................................................................................................................................
Comparons insertion2 et insertion3 pour une liste de 100 lments. La procdure time, utilise sans argument, retourne le temps machine en secondes depuis
le dbut de la session ; elle permet donc de chronomtrer une excution. On rpte
chaque tri 100 fois pour une comparaison signicative.
..................................................................................................................................
..................................................................................................................................
Le gain est rel mais peu important pour des listes de si petite taille, sans aucune
comparaison avec ce qui est fait usuellement sur machine. On ne peut faire plus
ici pour une autre raison, qu'il est encore bien plus important de comprendre.
Essayons d'utiliser notre tri pour une liste de 200 lments.
..................................................................................................................................
..................................................................................................................................
Ici, on avait oubli ce qui tait expliqu page 122 : on ne peut pas modier une
liste de plus de 100 lments ! Pour les tris consquents, les seuls dignes d'intrt,
il faut donc obligatoirement utiliser une technique tableau (array), autrement dit
vecteur (vector) dans le cas d'un seul indice.
159
..................................................................................................................................
..................................................................................................................................
On voit que le vecteur sert d'outil annexe, et que, en supposant que le cahier des
charges demande le rsultat sous forme de liste, on convertit le vecteur en liste en
n d'excution. Refaisons le mme test temps :
..................................................................................................................................
> st := time() :
for i from 1 to 100 do insertion4(list11) od :
time() - st ;
3.490
..................................................................................................................................
Le gain est trs consquent et on comprend bien maintenant pourquoi Maple vous
interdit de modier des listes longues : ces modications sont vritablement calamiteuses en optimisation temps et espace mmoire, et pour viter des dfauts
de rendement aux programmeurs inexpriments, Maple interdit purement et simplement de telles modications sauf pour de petites listes. Mme pour celles-ci
l'exemple vu ici montre que ce peut tre trs coteux si le mme phnomne est
rpt intensivement.
Rien n'empche maintenant de trier de longues listes. Une mthode nave
comme la ntre a un cot temps de tri grossirement proportionnel au carr du
nombre d'lments trier.
..................................................................................................................................
..................................................................................................................................
de sorte que les temps de tri deviennent vite importants. Les mthodes plus ruses
base d'arborescence sont beaucoup plus ecaces. Voir par exemple, pour un beau
traitement didactique du sujet, le chapitre 2 du livre de Wirth [7]. Comparer aussi
ce qui vient d'tre fait avec la procdure de tri propose par Maple lui-mme :
..................................................................................................................................
> time(sort(list11)) ;
0.45
..................................................................................................................................
160
Le temps de calcul est donc divis par 10000 ! On ne saurait mieux montrer que
Maple n'est pas vraiment fait pour la programmation de base. La programmation
interne de sort est en eet crite en C, avec une ecacit sans commune mesure,
d'une part parce que la technique de tri est autrement sophistique, d'autre part
parce que C est beaucoup plus proche du langage machine : notre programmation
est en eet interprte et l'ecacit par rapport ce qui est en fait disponible sur
machine est drisoire.
-o-o-o-o-o-o-
161
Chapitre 6
Procdures.
6.1 Introduction.
On a vu dans le chapitre prcdent un type de programmation itrative consistant rpter un certain nombre de fois une squence de programmation dans un
environnement lgrement variable d'une fois l'autre. La squence en question
doit alors tre encapsule dans une instruction do ... od. Le prsent chapitre
est consacr une autre forme de programmation itrative, en un sens trs dirent, consistant construire un objet procedure, appel plus simplement procdure,
puis l'utiliser de temps autre, quelquefois un grand nombre de fois, avec l
aussi un environnement un peu dirent d'une fois l'autre.
La principale dirence entre les deux cas est la suivante. Une suite d'instructions encapsule dans un do ... od est excute de faon rptitive un certain
nombre de fois puis dnitivement abandonne ; les guillemets de la qualication
dnitive sont ncessaires, parce que, pour d'autres raisons, cette itration peut en
fait tre nouveau excute ; cette instruction do peut tre par exemple son tour
encapsule dans un autre do ... od comme on l'a vu dans le chapitre prcdent
pour notre programmation du tri-insertion, voir Section 5.4. Une instruction do
peut aussi gurer dans une procdure, on a vu de nombreux exemples, de sorte
que la rexcution de la procdure impliquera en particulier une nouvelle excution
de l'instruction do.
Le caractre itratif d'une procdure est dirent. Il s'agit d'un ensemble d'instructions qu'on veut pouvoir excuter au besoin, n'importe quel moment.
Une terminologie bien dnie doit tre utilise en la matire, terminologie qu'on
prsente dans cette introduction, dont la signication sera dtaille dans ce chapitre. Quand une procdure est construite, elle ne sera utilisable que si elle est
installe dans l'environnement, accessible le plus souvent par l'intermdiare d'un
symbole appel alors, mais c'est un abus de langage, le nom de la procdure. Le
cas des procdures anonymes est aussi important : une telle procdure est alors
une composante d'un objet plus ou moins complexe, de nature quelconque, suite,
liste, ensemble, matrice, etc. Le cas d'une procdure gurant comme lment d'une
suite d'arguments d'un appel d'une autre procdure est frquent.
162
Quand une procdure est disponible, elle peut tre appele de diverses faons.
On dit alors qu'une invocation de la procdure est active. Cette invocation peut
tre active un temps trs court, moins d'une micro-seconde, ou un temps trs long,
plusieurs jours, avec bien sr tous les intermdiaires possibles. Trs important :
plusieurs invocations de la mme procdure peuvent tre actives au mme moment, mais au plus une est en cours d'excution ; les autres, bien qu'actives, sont
provisoirement au repos, en attente de la suite de leur excution ; c'est le point
cl de la programmation rcursive dont un exemple typique est la programmation de la procdure phi page 149. Quand une invocation de procdure termine,
cette invocation retourne toujours une valeur, quel que soit le cas de gure. Les
appels de procdures qui semblent ne rien retourner retournent en fait la suite
vide, celle qui est repre par le symbole NULL, et ceci doit alors presque toujours
tre explicitement prvu dans la dnition de la procdure. Une procdure peut
aussi retourner plusieurs objets, en fait une suite d'objets de longueur arbitraire.
Le mcanisme d'aectation multiple est alors souvent utilis pour dispatcher les
composantes du rsultat vers divers symboles.
Des symboles dits locaux sont souvent ajouts l'environnement lors de l'activation d'une procdure. Les autres symboles utiliss dans la procdure sont globaux. Par ailleurs des symboles locaux trs particuliers appels paramtres servent
particulariser le travail d'une invocation particulire de la procdure. Quand la
procdure est appele, des arguments sont passs la procdure, et les paramtres
de la procdure sont initialiss en fonction de ces arguments ; on verra que cette
description simplie est en fait assez incorrecte, mais chaque chose en son temps.
On a dj discut pour une autre raison la dirence entre ce que nous avons
appel argument provisoire et argument dnitif, voir la rgle Eval-14.
La partie locale de l'environnement peut son tour contenir des procdures
dont les rgles de visibilit sont alors particulires au contexte. Un tel objet, en
premire approximation local une procdure, peut nanmoins tre retourn
l'extrieur de la procdure, tout en gardant ses rgles de visibilit. Ces objets trs
tranges mnent la programmation fonctionnelle, inaccessible aux utilisateurs des
langages ordinaires, Pascal, C, C++ ou Java. C'est un outil trs puissant, ouvrant
un monde de programmation compltement nouveau, auquel le chapitre
sera
entirement consacr.
..................................................................................................................................
rsultat souhait.
..................................................................................................................................
> rho(20,21) ;
29
a2 + (b + c)2
..................................................................................................................................
Exploitons cette procdure, simple mais dj utile, pour expliquer les notions
les plus lmentaires.
123.456
..................................................................................................................................
Le symbole sigma est aussi prsent dans l'environnement et sa valeur est l'objet
float 123.456.
La forme output d'une procdure est un texte utilisant diverses polices et indentations pour tenter d'en faciliter la lecture. Notre procdure valeur de rho n'est
accessible que par valuation explicite, voir ce sujet la rgle Eval-16.
..................................................................................................................................
> rho ;
> eval(rho) ;
..................................................................................................................................
Un objet compos, comme une liste, une table, une matrice peut parfaitement
avoir comme composante une procdure. Ne pas croire qu'une telle situation est
articielle, elle ouvre des possibilits de programmation fonctionnelle trs intressantes qu'on examinera plus tard, largissant considrablement le domaine de la
programmation. Par exemple notre procdure repre par le symbole rho peut tre
un lment de liste :
..................................................................................................................................
..................................................................................................................................
29
..................................................................................................................................
..................................................................................................................................
L'expression encadre par les mots-cls proc et end, considrer comme parenthses ouvrante et fermante, est un constructeur de procdure pouvant gurer en
toute place o, aprs valuation, un objet procdure peut gurer. Une fois cette
procdure construite, Maple observe qu'elle doit tre applique la paire d'arguments 20 et 21, et le fait. Le rsultat est donc une nouvelle fois notre hypotnuse 29.
..................................................................................................................................
On a donc maintenant dans notre environnement onze symboles ayant pour valeur
le mme objet procdure, et il n'est donc pas correct de dire que son nom est l'un
ou l'autre de ces symboles. On mditera en particulier les comparaisons suivantes :
..................................................................................................................................
false
true
..................................................................................................................................
Inversement une procdure peut tre anonyme, autrement dit sans nom. On
verra plus tard que l'instruction suivante cre 100 procdures cres l'une aprs
l'autre par la procdure prdnie unapply, chacune levant son argument une
certaine puissance :
165
..................................................................................................................................
..................................................................................................................................
> ProcedureList[99] ;
(x x)99
> ProcedureList[10](2) ;
1024
> ProcedureList[20](3) ;
3486784401
..................................................................................................................................
De faon plus prcise la prsence contigu d'un objet et d'une parenthse ouvrante, sans sparateur, note un objet de type function, mme si aucune procdure
n'est en piste :
..................................................................................................................................
..................................................................................................................................
Les objets gurant entre parenthses sont les arguments (provisoires) ; il peut ne
pas y en avoir, mais les parenthses restent indispensables pour mriter le titre
function ; comparer ci-dessus les types de truc(), avec parenthses, et de truc, sans
parenthses.
De la mme faon, et c'est relativement frquent, une procdure peut tre sans
paramtre ; quand elle sera appele, il ne faudra donc donner aucun argument, mais
les parenthses doivent nanmoins gurer dans l'appel. Un exemple de procdure
sans argument est celle qui est retourne par la procdure rand, qu'on a dj utilise
plusieurs fois, voir par exemple page 40 pour initialiser une matrice alatoire.
Supposons que le contexte ncessite frquemment le tirage au sort d'un entier
entre -5 et +5. La procdure rand est disponible pour construire et retourner
une procdure capable d'eectuer ces tirages ; une telle procdure est appele un
gnrateur alatoire. Le plus simple consiste alors aecter la procdure ainsi
construite un symbole, par exemple rnd5 :
166
..................................................................................................................................
end
..................................................................................................................................
..................................................................................................................................
> rnd5() ;
4
..................................................................................................................................
comparer avec :
..................................................................................................................................
rnd5
rnd5 := proc()
local t; global _seed;
_seed := irem(427419669081 _seed, 999999999989);
t := _seed;
irem(t, 11) 5
end
..................................................................................................................................
24
..................................................................................................................................
Ici, l'valuateur appelle la procdure fact en lui passant l'argument 4 ; puisque cet
argument n'est pas nul, c'est la branche ngative de l'instruction if qui est excute, savoir RETURN(n*fact(n-1)) ; l'excution de cette instruction ncessite en
particulier l'valuation de fact(3) et l'valuateur va donc r -appeler la procdure
fact, cette fois avec l'argument 3 ; l'invocation initiale de fact est mise au repos,
167
et une nouvelle invocation est active, mais o cette fois l'argument pass est 3.
Le processus continue de la sorte jusqu' ce que cinq invocations soient actives,
appeles respectivement avec les arguments 4, 3, 2, 1 et 0. Pour cette dernire invocation c'est au contraire la branche positive de l'instruction if qui va tre excute
et l'instruction RETURN(1) est donc excute. Cette excution met n la dernire
invocation de fact, invocation qui retourne 1. La branche ngative de l'invocation
prcdente, essentiellement RETURN(1*fact(0)) peut alors tre termine ; l'appel
fact(0) a retourn 1 et cette avant-dernire invocation de fact va donc aussi
retourner 1. La troisime invocation est ractive, qui tait arrte par l'instruction
RETURN(2*fact(1)) ; la quatrime invocation de fact vient justement de retourner
1, et la troisime va donc elle aussi terminer son excution et retourner 2. Selon le
mme processus, la seconde invocation de fact va retourner 6 et enn la premire
va retourner 24.
On peut mettre en vidence ce dispositif tiroirs en demandant d'excuter
la procdure fact en mode debug.
..................................................................................................................................
> debug(fact) ;
> fact(4)
{--> enter fact, args
{--> enter fact, args
{--> enter fact, args
{--> enter fact, args
{--> enter fact, args
<-- exit fact (now in
<-- exit fact (now in
<-- exit fact (now in
<-- exit fact (now in
<-- exit fact (now at
fact
= 4
= 3
= 2
= 1
= 0
fact) = 1}
fact) = 1}
fact) = 2}
fact) = 4}
top level) = 24}
24
..................................................................................................................................
168
> evenfact(4)
{--> enter evenfact, args = 4
{--> enter oddfact, args = 3
{--> enter evenfact, args = 2
{--> enter oddfact, args = 1
{--> enter evenfact, args = 0
<-- exit evenfact (now in oddfact) =
<-- exit oddfact (now in evenfact) =
<-- exit evenfact (now in oddfact) =
<-- exit oddfact (now in evenfact) =
<-- exit evenfact (now at top level)
1}
1}
2}
6}
= 24}
24
..................................................................................................................................
Il est presque toujours ncessaire, quand les expriences souhaites sont termines, de dsactiver le mode debug d'une procdure. Il faut alors utiliser la procdure
undebug en donnant comme argument(s) le(s) nom(s) de procdure(s) en question.
..................................................................................................................................
> undebug(fact)
fact
> fact(5) ;
120
..................................................................................................................................
..................................................................................................................................
> floor(log[10](fact(600))) + 1 ;
> floor(log[10](itfact(600))) + 1 ;
1409
..................................................................................................................................
> floor(log[10](100.000)) + 1 ;
> floor(log[10](99.999)) + 1 ;
2
> floor(log[10](0.00123)) + 1 ;
2
..................................................................................................................................
170
a, b, c := 3, 4, 5
3 10
..................................................................................................................................
Ici, x et y sont des paramtres sans spcication de type, et le passage d'argument par valeur et substitution va donc s'appliquer. Quand la procdure rho est
appele, deux arguments provisoires sont prvus, le symbole a et l'expression b+c.
L'valuateur de Maple est donc mis d'abord deux fois au travail pour produire les
arguments dnitifs, donc dans ce cas, vu les aectations pralables aux symboles
a, b et c, les arguments dnitifs vont tre 3 et 9.
Cette phase pralable tant ralise, avant d'appeler la procdure rho, Maple
fait encore un autre travail : il substitue dans le texte de la procdure toute occurence de x par 3 et toute occurence de y par 9. Le texte de la procdure pour la
nouvelle invocation devient donc :
..................................................................................................................................
RETURN(sqrt(3^2 + 9^2))
..................................................................................................................................
Il est important ici de comprendre qu'il y a bien eu un mcanisme de substitution de l'argument au paramtre, et non pas de mise--jour de l'environnement
l'aide des arguments, comme il est si tentant de le croire. Beaucoup de langages,
C et Lisp notamment, modient l'environnement visible de l'intrieur de la procdure pour y ajouter dans un tel cas de gure de nouveaux chanages [x 3] et
[y 9], cachant ventuellement des chanages externes de mme source. Maple
est de ce point de vue trs dirent. Pour s'en convaincre, il faut faire deux expriences.
La premire est l'origine des plus mmorables crises de nerfs des utilisateurs
de Maple. Les calculs trs lmentaires suivants peuvent tre eectus hors procdure :
..................................................................................................................................
> a := 5 ; a := a+a ;
a := 5
a := 10
> a := b ; a := a + a ;
a := b
a := 2b
..................................................................................................................................
Ces calculs sont si lmentaires que le lecteur s'interroge probablement sur leur
intrt ; mais considrez la version suivante des mmes calculs l'intrieur d'une
procdure.
..................................................................................................................................
> restart :
exp1 := proc(a)
a := a + a ;
RETURN(a)
end :
> exp1(5) ;
> exp1(b) ;
> b ;
Error, too many levels of recursion
..................................................................................................................................
Si vous n'avez pas d'explication, vous aurez probablement les plus grandes
peines comprendre ces rsultats. Celui qui croit un passage par valeur et
aectation une variable a interne la procdure est bien incapable d'expliquer
ces phnomnes si tranges. Il faut absolument interdire cette interprtation, et
revenir la seule valide, le mcanisme de substitution. Quand la procdure exp1 a
t appele avec l'argument 5, le texte de la procdure est devenu :
..................................................................................................................................
5 := 5 + 5 ;
RETURN(5)
..................................................................................................................................
parameter, que nous appelons simplement paramtre. Cet usage n'est pourtant pas
si illgal que a, comme on va le voir immdiatement.
Quand exp1(b) est appel, comme b est alors un symbole libre, l'argument
dnitif est aussi le symbole b, de sorte que le texte de la procdure invoque
devient :
..................................................................................................................................
b := b + b ;
RETURN(b)
..................................................................................................................................
Conseil 28 Bien que ce ne soit pas toujours erron, au sens strict du terme,
ne cherchez pas modier la valeur d'un paramtre par une instruction d'aectation, notion qui est en fait non sens. Si vous avez vraiment besoin de faire varier
cette pseudo-valeur, doublez ce paramtre d'une variable locale et commencez par
initialiser cette variable comme il se doit.
> a, b := 2, 3 ;
a, b := 2, 3
> a, b := b, a ;
a, b := 3, 2
> a, b ;
3, 2
..................................................................................................................................
crire une procdure swap ralisant la mme chose d'une faon sensiblement
plus lisible est une ide naturelle.
..................................................................................................................................
> a, b := 2, 3 ;
a, b := 2, 3
> swap(a, b) ;
> a, b ;
3, 2
..................................................................................................................................
..................................................................................................................................
a, b := 2, 3
> swap(a,b) ;
Error, (in swap) illegal use of a formal parameter
..................................................................................................................................
2, 3
..................................................................................................................................
Cette fois l'erreur est vite, mais la procdure est sans eet sur les aectations
de a et b ; seules les aectations internes la procdure ont t modies. Il faut
donc ncessairement s'organiser pour passer les symboles eux-mmes et non pas
leur valeur. C'est un peu audacieux, car le conseil ci-dessus n'est plus respect. De
plus l'appel de swap doit citer les symboles quots, car leur valuation doit tout
prix tre empche. D'o cette (tentative de) solution.
..................................................................................................................................
Error, swap expects its 1st argument, a, to be of type symbol, but received 2
..................................................................................................................................
> eval([a,b], 1) ;
[b, a]
1 Une
174
..................................................................................................................................
> a, b := 2, 3 ;
a, b := 2, 3
> swap := proc(x::symbol, y::symbol)
x, y := eval(y), eval(x) ;
RETURN(NULL)
end :
> swap('a', 'b') ;
> a, b ;
3, 2
..................................................................................................................................
Mais cette solution est peu lgante : les quotes toujours ncessaires dans
l'appel sont franchement pnibles. C'est prcisment dans une telle situation qu'il
faut songer l'autre mthode disponible de passages d'arguments, qu'on examinera
un peu plus loin.
..................................................................................................................................
[1, 2, 3, 1, 2, 3]
..................................................................................................................................
Cette procdure exercice met bout bout deux exemplaires de la liste argument. En mal d'inspiration pour le nom du paramtre, pourquoi ne pas choisir
simplement list ? Or ceci est tout--fait lgal pour un nom de paramtre, comme
on peut le voir. Les utilisateurs prennent ainsi rapidement l'habitude d'appeler set
l'unique paramtre ensemble, matrix l'unique paramtre matrice, etc. Mais considrons le petit exercice suivant. Soit crire une procdure liminant les doublons
d'une liste d'entiers, et triant la liste d'entiers rsultante.
175
..................................................................................................................................
..................................................................................................................................
La conversion en ensemble (set) limine automatiquement les ventuels doublons, voir page 108 ; ceci fait, on reconvertit l'ensemble obtenu en liste, qu'enn
on trie. Essai :
..................................................................................................................................
> clean([2,1,2,3]) ;
Error, (in clean) wrong number (or type) of parameters in function convert
..................................................................................................................................
La procdure convert est en dlicatesse. Un examen soigneux montre immdiatement la confusion : le deuxime argument list du convert externe est valu
avant d'tre utilis, car convert est une procdure standard. L'erreur est facile
corriger : pour empcher cette valuation intempestive, il sut de quoter cette
occurence-l du symbole list :
..................................................................................................................................
Error, (in clean) wrong number (or type) of parameters in function convert
..................................................................................................................................
> unprotect(list) ;
> list := [2,1,2,3] ;
list := [2, 1, 2, 3]
> sort(convert(convert(list, set), 'list')) ;
[1, 2, 3]
..................................................................................................................................
et on constate que cette fois l'erreur ne se produit pas. Nous sommes l dcidment
dans un cas de debugging plus que svre ! Mais que peut bien expliquer tout cela ?
L'erreur commise ici rsulte d'une incomprhension fondamentale du mcanisme de transmission argument vers paramtre. Il est erron de penser que le
paramtre est un symbole ayant, lors d'une valuation, telle valeur dduite de l'argument dnitif. Ce n'est pas le bon point de vue, et c'est cette erreur de point
de vue qui engendre ces birarreries en srie. En fait le paramtre est une composante de texte, et l'argument est substitu cette composante de texte paramtre
l'invocation de la procdure. Pour provoquer hors procdure la mme erreur, il
176
> eval(subs('list'=list,
'sort(convert(convert(list, set), 'list'))')) ;
Error, wrong number (or type) of parameters in function convert
..................................................................................................................................
> subs('list'=list,
'sort(convert(convert(list, set), 'list'))') ;
sort(convert(convert([2, 1, 2, 3], set),0 [2, 1, 2, 3]0 ))
> eval(%) ;
Error, wrong number (or type) of parameters in function convert
..................................................................................................................................
test
> test(argument) ;
{--> enter test, args = argument
var := argument
argument
..................................................................................................................................
On voit ici que les quotes n'ont pas empch la substitution de parameter par
argument.
Revenons notre exemple initial. La seule faon de le debugger si on veut
garder le mme style de programmation consiste ne pas utiliser le symbole list
comme paramtre. On commence d'abord par remettre le symbole list dans son
tat normal, sans valeur et protg.
..................................................................................................................................
..................................................................................................................................
Autre mthode bien amusante, mais qu'on ne peut pas dcemment conseiller :
177
..................................................................................................................................
..................................................................................................................................
178
..................................................................................................................................
> restart :
> swap := proc(x::uneval, y::uneval)
x, y := eval(y), eval(x) ;
RETURN(NULL)
end :
> a, b := 2, 3 ;
a, b := 2, 3
> swap(a,b) ;
> a, b ;
3, 2
..................................................................................................................................
..................................................................................................................................
..................................................................................................................................
> whattype(''expr'') ;
uneval
..................................................................................................................................
Noter qu'il a t indispensable de quoter deux fois pour qu'il reste une expression
quote aprs valuation de l'argument, car whattype est une procdure standard ;
comparer avec :
..................................................................................................................................
> whattype('expr') ;
symbol
..................................................................................................................................
La nouvelle procdure swap est assez technique, typique de ce type de manipulation de chanage, et va aussi mettre en vidence un caractre particulier aux
symboles locaux.
179
..................................................................................................................................
;
;
be a name`, xx) fi ;
be a name`, yy) fi ;
..................................................................................................................................
> a, b := 2, 3 ;
a, b := 2, 3
> swap(a, b) ; a, b ;
arg1 = a, arg2 = b, xx = a, yy = b, xval = 2, yval = 3
3, 2
> swap('a', 'b') ; a, b ;
arg1 = 0a0 , arg2 = 0b0 , xx = a, yy = b, xval = 3, yval = 2
2, 3
> swap(a, a+b) ;
Error, (in swap) a+b should be a name.
D'abord il a fallu utiliser des variables locales xx et yy pour pouvoir manipuler les arguments, surtout supprimer les quotes ventuels : ils sont reprs par
type(..., uneval) et le cas chant, ils sont supprims par xx := op(1, xx), qui
extrait l'unique oprande, donc l'objet entre quotes. Demander xx := xx est insufsant, parce que pour un symbole local, un seul niveau d'valuation est eectu,
de sorte que la valeur de xx resterait en fait inchange.
Eval 29 Un symbole local une procdure ne suit pas la rgle Eval-7 ; quand il
est valu, le rsultat est seulement le but du chanage correspondant ; en particulier
ce but n'est pas rvalu.
Considrez l'exemple suivant, trs exotique, pour mettre en vidence cette particularit des symboles locaux par rapport l'valuateur.
180
..................................................................................................................................
> restart ;
> c := d ;
c := d
> a ;
Le symbole a avait t dclar global et continue vivre en dehors de la procdure, valeur conserve. Les eval(a,-) permettent de suivre la chane de. . . chanages partant de a. En particulier le symbole b, en principe local la procdure
test, reste accessible de l'extrieur, par l'intermdiaire de a, alors que l'invocation
de la procdure qui avait cr ce symbole est acheve ! Si on compare ce symbole b
l un symbole b banal, on constate qu'ils sont dirents ! Notre environnement
181
a maintenant deux symboles de mme nom, dont l'un est accessible seulement par
l'intermdiaire de a. On constate d'ailleurs que l'ensemble constitu de ces deux
symboles a bien deux lments : pas d'limination de doublon puisqu'il n'y a pas
de doublon ! On vrie enn que les adresses machines de ces symboles sont bien
direntes.
Ces questions ne sont en aucune faon articielle. Frquemment quand une
procdure retourne par exemple une matrice, on cite seulement le symbole reprant
cette matrice, et en raison de la rgle Eval-16, le symbole seul est retourn.
nouveau, des crises de nerfs sont proches si on compare ces deux exemples.
..................................................................................................................................
> evalm(A) ;
A
..................................................................................................................................
Dans ce premier essai, l'utilisation de evalm ne permet pas d'atteindre la matrice qui avait t aecte A. Le point, c'est que le symbole retourn, local, est
dirent du symbole A argument de evalm ! Comparez avec cet autre essai :
..................................................................................................................................
> B := testm() ;
B := A
> evalm(B) ;
1 2
3 4
..................................................................................................................................
Cette fois la valeur de B est le bon symbole A, de sorte que evalm atteint le but
recherch. Avez-vous bien compris toutes ces choses ? Si oui, vous ne rsisterez pas
tenter ceci :
..................................................................................................................................
> A := testm() ;
A := A
> eval(A,1) ;
A
> eval(A,2) ;
1 2
3 4
..................................................................................................................................
argument une suite de rels ; l'utilisateur a l'impression, pas compltement justie, que cette procdure admet un nombre quelconque d'arguments . Programmons
nous-mme cette procdure pour montrer le principe.
..................................................................................................................................
> my_max(4,6,5) ;
3
4, 6, 5
6
..................................................................................................................................
Le principe est fort simple. Deux variables locales sont disponibles dans toute
procdure, nargs et args. Elles sont automatiquement initialises par Maple
chaque invocation de la procdure. La premire, nargs, a pour valeur le nombre
d'arguments passs l'appel de cette invocation, ou plus prcisment la longueur
de la suite qui est en fait l'unique argument vritable, voir ce qui a dj t expliqu
propos des suites d'arguments Section 4.4.
Bien comprendre que ce mcanisme est disjoint de l'utilisation standard des
arguments, l'aide de la liste de paramtres proc(prm1, prm2, ...). Ici, dans
la procdure my_max, on n'a mme prvu aucun paramtre, la liste d'arguments
tant entirement gre par l'intermdiaire des variables nargs et args. Noter la
programmation complte conssistant considrer comme lgal un appel de la procdure my_max sans argument, ce qui est d'ailleurs trait de la mme faon par la
procdure ocielle max, essayez.
Pour rendre plus visible ce mcanisme, la programmation donne ici de my_max
ache au dvut de l'activation de la procdure les valeurs des variables nargs et
args.
Rien n'empche de combiner le mcanisme banal base de symboles paramtres
et les informations disponibles par l'intermdiaire des variables implicites nargs et
args.
Commenons par un exemple articiel mais didactique.
183
..................................................................................................................................
..................................................................................................................................
On a pass quatre arguments la procdure, dont deux ont t lus par l'intermdiaire des paramtres prm1 et prm2, et les autres par celui de la variable args ;
leur nombre a t dduit de nargs.
Comme application signicative de ce mcanisme, reprenons le problme de
la programmation rcursive de la procdure mylog10 de la page 149. On avait
not le danger, trs rel, d'une variable globale epsilon dnie par la procdure
matresse mylog10, puis utilise par la procdure moteur phi : si l'utilisateur a
pour d'autres raisons une variable dj baptise epsilon, l'ancienne valeur de cette
variable serait perdue ! Le nom de procdure phi n'est pas non plus bien fantastique
et risque d'interfrer avec un autre symbole. On pourrait utiliser ici pour mettre en
vidence la dpendance de la seconde procdure un nom plus explicite ce propos
comme `mylog10/phi` ; Maple utilise souvent lui-mme cette technique pour ses
propres procdures. Autre problme : la prcision associe la variable epsilon
n'est pas modiable, alors qu'il serait bien plus intressant de laisser l'utilisateur
la possibilit ventuelle de prfrer une autre prcision.
On va solutionner l'ensemble de ces problmes comme suit :
..................................................................................................................................
184
>
>
>
>
..................................................................................................................................
> Digits := 10 :
> phi, epsilon := 56, 0.01 ; mylog10(3) ; phi, epsilon ;
, := 56, .01
.4771212547
56, .01
..................................................................................................................................
..................................................................................................................................
Pour une raison ou une autre, cette couleur peut tre juge non satisfaisante ;
Maple vous donne la possibilit d'un troisime argument, optionnel, permettant
de demander une autre couleur.
185
..................................................................................................................................
..................................................................................................................................
On a utilis ici l'argument mot-cl color. Noter que l'unique argument supplmentaire est l'objet de type equation color=blue, donc un seul objet oprateur
`=', et oprandes color et blue. C'est la procdure plot qui analyse cet argument, en dduit notamment qu'il s'agit de modier la couleur par dfaut, et fait
le ncessaire pour tenir compte de l'indication blue qui est donne.
Un grand nombre d'arguments mot-cl sont disponibles pour les procdures
graphiques, donnant beaucoup de possibilits l'utilisateur pour obtenir telle ou
telle particularit dans le rsultat. Par exemple on peut en plus souhaiter un trac
plus pais (argument mot-cl thickness) et en trait non continu (argument
mot-cl linestyle).
..................................................................................................................................
..................................................................................................................................
Voir la page de documentation plot,options pour avoir une ide des diverses
possibilits proposes, assez vastes. Ce qui est trs commode dans ces arguments
mot-cl, c'est le fait qu'ils sont utilisables en nombre arbitraire et dans un ordre
arbitraire. Comparer le trac prcdent avec le suivant.
..................................................................................................................................
..................................................................................................................................
Il serait en eet franchement dsagrable de contraindre l'utilisateur prciser tous les arguments optionnels et avec un ordre impos ; on prfre dnir
ces arguments par dfaut, et laisser l'utilisateur la possibilit d'en modier un
nombre quelconque en gnral assez modeste. Comment obtenir un tel rsultat
dans l'criture d'une procdure ?
186
Prenons par exemple le cas d'une procdure de traitement de liste assez souvent
utile retournant la position de tel lment, premier argument, dans telle liste,
deuxime argument. La programmation la plus simple peut-tre la suivante.
..................................................................................................................................
..................................................................................................................................
Ceci dit un certain nombre d'options donnes l'utilisateur pourraient augmenter sensiblement la porte de cette procdure. En particulier on peut donner
la possibilit de prciser une fonction de comparaison dirente de l'galit usuelle
pour la comparaison entre l'lment chercher et les lments de liste examiner. On pourrait donc comme dj fait utiliser un troisime argument optionnel ; si
l'argument ne gure pas, on utilise la comparaison standard, sinon la comparaison
propose.
..................................................................................................................................
..................................................................................................................................
Mais d'autres options sont tentantes pour le dveloppeur. Par exemple on peut
aussi demander de ne considrer qu'une sous-liste de la liste argument, considrant
que le reste de la liste n'est pas concern par la recherche de position. On peut
aussi considrer plus intressant dans certains cas de commencer par la n. On
voit que les combinaisons d'options peuvent tre trs varies et c'est justement le
cas o il faut penser arguments mots-cls.
On va ici prvoir quatre arguments mot-cl :
cmpr : pour une fonction de comparaison dirente de la comparaison standard.
187
..................................................................................................................................
188
..................................................................................................................................
..................................................................................................................................
On note l'inuence dsastreuse d'une ventuelle valeur pour un symbole motcl ; si, par mgarde, le mot-cl strt a une valeur, ici 7, alors l'argument mot-cl
est inoprant ; c'est une source permanente de bugs quelquefois assez pervers sous
Maple, qu'on retrouve ici sous une forme un peu dirente. Comparer avec :
..................................................................................................................................
> color := 56 ;
color := 56
..................................................................................................................................
Le point de vue de Maple est en eet un peu dirent ; il considre que tous les
arguments partir du troisime sont des arguments mot-cl, mais il ne reconnat
pas dans l'entier 56, valeur du symbole color, un mot-cl lgal enregistr et
189
signale une erreur de cohrence. Maple signale qu'on peut viter ce type d'erreur
en empchant l'valuation du symbole color ; c'est exact mais reste assez lourd3 .
..................................................................................................................................
..................................................................................................................................
-o-o-o-o-o-o-
3 Les
langages plus volus commme Common Lisp ont un espace particulier de symbolesmots-cls, notion trop dlicate techniquement pour le grand public Maple. . .
190
Chapitre 7
Graphiques.
7.1 Introduction.
Comme (presque) tout logiciel mathmatique grand public, Maple permet
la ralisation assez commode de graphiques mathmatiques de toutes sortes. Le
mcanisme sous-jacent est astucieux et lgant et donne des moyens assez puissants
aux dveloppeurs. Le principe est le suivant ; les procdures graphiques Maple
produisent des objets (pseudo-) fonctions particuliers dont l'oprateur matre est
le symbole PLOT. Ceci fait, si jamais l'utilisateur Maple, inconsciemment (cas
le plus frquent) ou consciemment, demande l'impression de l'objet en question,
Maple ache le graphique probablement souhait par l'utilisateur.
Pour mettre en vidence cette tehnique, le truc consiste aecter un symbole exprience la valeur d'une instruction graphique ; en premire approximation,
cette instruction apparat comme telle, mais en fait il s'agit d'une procdure banale
retournant un objet de type function o l'oprateur matre est le symbole PLOT.
Reprenons le trac ftiche de la fonction sinus de 0 2 :
..................................................................................................................................
..................................................................................................................................
191
..................................................................................................................................
..................................................................................................................................
On voit ainsi que l'objet retourn par la procdure plot est un objet function
dont l'oprateur est le symbole PLOT, le premier argument est son tour un objet
function dont l'oprateur est cette fois le symbole CURVES (on a renonc ici le
montrer compltement), etc. On voit ainsi la structure interne de l'objet retourn
par la procdure plot o, strictement parlant, aucun nouveau type de donne
est impliqu. C'est seulement la composante print (voir Section 2.2.2) du cycle
read-eval-print qui reconnat un traitement particulier : si jamais l'objet function
acher en sortie a l'oprateur PLOT, c'est qu'il s'agit d'un objet reprsentant
selon un codage pas si compliqu un graphique, de sorte que l'achage graphique
appropri de cet objet est donn l'cran. Pour mettre ce dernier point en vidence,
demandons l'achage de la valeur du symbole result :
..................................................................................................................................
> result ;
..................................................................................................................................
Par comparaison avec le cas de l'instruction prcdente, on voit que cet achage graphique n'est obtenu que si l'unique objet acher est de ce type, sinon
l'achage banal est prfr. Voir par exemple l'achage de la suite deux lments
o le second est encore la valeur du symbole result :
..................................................................................................................................
> 1, result ;
1, PLOT(CURVES([[0, 0], [.1369555585245651, .1365278179668514],
... ...
..................................................................................................................................
De la sorte, les objets graphiques peuvent tre manipuls comme tout objet
Maple. Comme exemple simple, transformons titre d'exercice notre courbe rouge
en courbe bleue ; il sut pour ce faire de modier l'oprande COLOUR de notre objet
graphique ; ceci est obtenu par substitution, et ici on ache immdiatement l'objet
transform :
192
..................................................................................................................................
..................................................................................................................................
Le mode RGB pour la couleur de l'objet graphique est un triplet de rels compris
entre 0 et 1 donnant un indice pour chacune des trois couleurs fondamentales,
rouge, vert (green) et bleu. Par dfaut, un seul objet graphique est le plus souvent
ach en rouge pur, donc indices RGB = (1, 0, 0) ; on comprend ainsi comment
le rsultat aprs substitution est au contraire ach en bleu.
Comme autre exercice, on va manipuler la liste des points de notre courbe
sinusodale comme suit : on va changer la premire et la deuxime coordonne,
ralisant donc une symtrie par rapport la premire bissectrice des deux axes,
puis on augmente la premire coordonne obtenue d'une unit. Ceci peut tre
obtenu par la suite de manipulations lmentaires suivantes dont on cache les
rsultats. D'abord on extrait la composante CURVES, dont on extrait ensuite la liste
des points. Un coup de map permet de faire facilement la transformation souhaite,
optenant la liste appele points2. On construit par substitution un nouvel objet
CURVES, puis un nouvel objet PLOT qu'enn on ache :
..................................................................................................................................
>
>
>
>
>
>
..................................................................................................................................
193
Bibliographie
[1] Alfred V. Aho, John E. Hopcroft, Jerey D. Ullman. The design and analysis
of computer algorithms. Addison-Wesley, 1974.
[2] Patrick Dehornoy, Complexit et dcidabilit. Springer, 1993.
[3] Andrew Hodges. Alan Turing : the enigma of intelligence. Burnett Books
Limited, 1983.
[4] Serge Lang. Algebra. Addison-Wesley, 1965.
[5] Patrice Naudin et Claude Quitt. Algorithmique Algbrique. Masson, 1992.
[6] Lionel Schwartz. Mathmatiques pour la Liccence, Algbre. Dunod, 1998.
[7] Niklaus Wirth. Algorothms + Data Structures = Programs. Prentice Hall,
1976.
194