L’environnement de programmation
fonctionnelle DrRacket
Stéphane Legrand < stephleg@free.fr >
Décembre 2011
Résumé
Nous co...
Table des matières
1 Introduction 3
2 Le langage Racket 4
2.1 Support des exceptions . . . . . . . . . . . . . . . . . . ....
Chapitre 1
Introduction
DrRacket (appelé DrScheme jusqu’en 2010) est un environnement de déve-
loppement disponible sous l...
Chapitre 2
Le langage Racket
On retrouve bien évidemment toutes les caractéristiques du langage Scheme.
Même syntaxe simpl...
2.2. Programmation objets 5
dont l’utilisation dans une session DrRacket donnera ceci :
2.2 Programmation objets
Racket su...
2.2. Programmation objets 6
22
23 ; méthode privée : additionne l’argument v à l’attribut x
24 (define/private (ajout_x v)...
2.3. La programmation par contrats 7
La notion d’interface est également présente. Une classe peut indiquer qu’elle
implém...
2.3. La programmation par contrats 8
8 ; fonctions qui vérifient les contraintes du contrat
9 (define test_arg? number?)
1...
2.4. Les modules et les "units" 9
2.4 Les modules et les "units"
Les modules [9] permettent de fournir des bibliothèques d...
Chapitre 3
Fonctions graphiques
DrRacket propose nativement plusieurs bibliothèques de fonctions gra-
phiques. Nous allons...
3.2. GUI 11
18 ; rectangles_vc : rectangles centrés verticalement
19 (define (rectangles_vc) (rectangles 120 vc-append))
2...
3.2. GUI 12
9
10 ; Texte à l’intérieur de la fenêtre
11 (define message (new message% [parent fenetre]
12 [label "Cliquez ...
3.3. PLoT 13
3.3 PLoT
PLoT [17] permet de réaliser un programme qui va décrire un graphique et
produire en sortie une imag...
3.3. PLoT 14
17 #:y-max 500
18 #:x-label "Mois"
19 #:y-label "C.A. ventes")
chargé et exécuté dans DrRacket affichera ce gr...
Chapitre 4
Déboguage
L’environnement DrRacket inclue un outil de déboguage [20] qui permet de
dérouler pas à pas le progra...
Déboguage 16
Exemple
Dans l’exemple ci-dessus, la session de déboguage montre que l’exécution
du programme est arrêtée à l...
Chapitre 5
Extension de l’environnement
5.1 Les plugins
Les plugins [21] permettent de modifier l’interface et/ou les fonct...
5.1. Les plugins 18
4 racket/gui/base
5 racket/unit
6 mrlib/switchable-button
7 plot)
8 (provide tool@)
9
10 (define tool@...
5.1. Les plugins 19
58 (define (phase1) (void))
59 (define (phase2) (void))
60
61 (drracket:get/extend:extend-unit-frame b...
5.2. Les macros 20
5.2 Les macros
Racket supporte la création de macros [22] qui permettent de définir des
transformations ...
5.3. Les langages 21
5.3 Les langages
Dans les cas où l’utilisation des macros est insuffisante, Racket permet
relativement...
5.3. Les langages 22
DSL pour Domain Specific Language) comme l’implémentation d’un jeu
d’aventure en mode texte [25]. Ce d...
Chapitre 6
Conclusion
Racket est un langage historiquement fonctionnel puisque très proche du
Scheme. Il intègre d’autres ...
Conclusion 24
On voit que l’utilisation du langage Scheme est relativement plus élevée
par rapport à d’autres langages fon...
Références
[1] Robert Bruce Findler and Jacob Matthews. The revised6 report on the
algorithmic language scheme, 2011. http...
Références 26
[16] The racket graphical interface toolkit, 2011. http://docs.racket-lang.
org/gui/index.html.
[17] Plot : ...
Prochain SlideShare
Chargement dans…5
×

L’environnement de programmation fonctionnelle DrRacket

850 vues

Publié le

L’environnement de programmation
fonctionnelle DrRacket

Publié dans : Logiciels
1 commentaire
0 j’aime
Statistiques
Remarques
  • Pour complément le livre "Premiers Cours de Programmation avec Racket" de JP. Roy chez Ellipses (2010)
       Répondre 
    Voulez-vous vraiment ?  Oui  Non
    Votre message apparaîtra ici
  • Soyez le premier à aimer ceci

Aucun téléchargement
Vues
Nombre de vues
850
Sur SlideShare
0
Issues des intégrations
0
Intégrations
8
Actions
Partages
0
Téléchargements
12
Commentaires
1
J’aime
0
Intégrations 0
Aucune incorporation

Aucune remarque pour cette diapositive

L’environnement de programmation fonctionnelle DrRacket

  1. 1. L’environnement de programmation fonctionnelle DrRacket Stéphane Legrand < stephleg@free.fr > Décembre 2011 Résumé Nous commencerons par décrire succintement l’environnement DrRa- cket puis nous verrons certains aspects particuliers du langage principal qui lui est associé. Nous approfondirons ensuite les fonctionnalités gra- phiques proposées ainsi que l’outil de déboguage et d’évaluation pas à pas. Enfin nous verrons comment il est possible d’étendre l’environne- ment DrRacket. 1
  2. 2. Table des matières 1 Introduction 3 2 Le langage Racket 4 2.1 Support des exceptions . . . . . . . . . . . . . . . . . . . . . . 4 2.2 Programmation objets . . . . . . . . . . . . . . . . . . . . . . . 5 2.3 La programmation par contrats . . . . . . . . . . . . . . . . . 7 2.4 Les modules et les "units" . . . . . . . . . . . . . . . . . . . . 9 3 Fonctions graphiques 10 3.1 Slideshow . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 10 3.2 GUI . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 11 3.3 PLoT . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 13 4 Déboguage 15 5 Extension de l’environnement 17 5.1 Les plugins . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 17 5.2 Les macros . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 20 5.3 Les langages . . . . . . . . . . . . . . . . . . . . . . . . . . . . 21 6 Conclusion 23 Références 25 2
  3. 3. Chapitre 1 Introduction DrRacket (appelé DrScheme jusqu’en 2010) est un environnement de déve- loppement disponible sous licence LGPL pour les plates-formes Windows, Macintosh et Unix. Historiquement très utilisé pour l’apprentissage des langages fonctionnels, cet environnement de développement propose une interface graphique basique avec notamment une coloration syntaxique du code et un debugger intégré. Il offre également une très bonne interactivité avec l’utilisateur. En effet, il suffit de saisir le code et de cliquer sur le bouton "Exécuter" pour immédiatement voir apparaître le résultat de l’exécution. Y compris si le résultat consiste en une image. Le principal langage supporté est Racket, un dialecte Scheme. Pour l’exé- cution des programmes, nous disposons à la fois d’un interpréteur et d’un compilateur qui est capable de produire soit un binaire au format "bytecode" qui sera alors exécuté par la machine virtuelle Racket soit directement un exécutable natif. DrRacket propose également le support d’autres langages plus ou moins proches du langage Racket comme le Scheme au standard R5RS ou R6RS [1] [2], un Scheme avec typage [3], le langage Datalog [4] pour les bases de données déductives ou bien encore Scribble [5], un langage spécialisé dans la création de documents HTML ou PDF. Plus largement, il est possible de développer son propre langage pour l’ajouter dans DrRacket (voir la section 5.3 page 21). 3
  4. 4. Chapitre 2 Le langage Racket On retrouve bien évidemment toutes les caractéristiques du langage Scheme. Même syntaxe simple et à parenthèses, notation préfixée pour les opérateurs, optimisation des récursions terminales ("tail recursion"). Tous les objets du langage sont dits de première classe et peuvent être manipulés de la même manière. Il est ainsi possible pour une fonction de prendre en paramètre ou de renvoyer une autre fonction. Racket offre par ailleurs plusieurs fonctionnalités supplémentaires par rap- port au langage Scheme de base. Nous allons maintenant en détailler quelques- unes. 2.1 Support des exceptions Racket permet la gestion d’exceptions [6] lors de l’exécution d’un programme. Une exception est normalement définie par une structure de données de type "exn" mais il est possible de lever n’importe quelle valeur en tant qu’exception. On utilise la fonction "with-handlers" pour capturer une exception. Voici un exemple : 1 #lang racket 2 ; exception de type exn:fail 3 (define mon_exception (lambda error "OUPS !")) 4 (define (test v) 5 ; on capture uniquement le "raise 999" 6 (with-handlers 7 ([(lambda (e) (equal? e 999)) (lambda (e) "Exception 999 attrapée !")]) 8 (match v 9 ; si v = "A" : aucune exception 10 ["A" (display v)] 11 ; si v = 1 : lève une exception avec la valeur 999 12 [1 (raise 999)] 13 ; dans tous les autres cas, lève l’exception mon_exception 14 [_ (raise (mon_exception))]))) 4
  5. 5. 2.2. Programmation objets 5 dont l’utilisation dans une session DrRacket donnera ceci : 2.2 Programmation objets Racket supporte la programmation objets [7] avec les notions de classes, d’héritages, de constructeurs, de surcharges de méthodes et de portée des méthodes (publiques, privées) : 1 #lang racket 2 (define maclasse% ; par convention, un nom de classe se termine par % 3 (class object% ; hérite de la classe racine "object" 4 ; constructeur 5 ; x et y sont des arguments du constructeur 6 (init init_x init_y) 7 8 ; attribut privé de la classe nommé x 9 ; sa valeur est initialisée avec l’argument init_x du constructeur 10 (define x init_x) 11 ; attribut privé de la classe nommé y 12 ; sa valeur est initialisée avec l’argument init_y du constructeur 13 (define y init_y) 14 15 ; appel du constructeur de la classe parente 16 (super-new) 17 18 ; méthode publique : renvoie la valeur de l’attribut x 19 (define/public (get_x) x) 20 ; méthode publique : renvoie la valeur de l’attribut y 21 (define/public (get_y) y)
  6. 6. 2.2. Programmation objets 6 22 23 ; méthode privée : additionne l’argument v à l’attribut x 24 (define/private (ajout_x v) 25 (set! x (+ x v))) 26 27 ; méthode privée : additionne l’argument v à l’attribut y 28 (define/private (ajout_y v) 29 (set! y (+ y v))) 30 31 ; méthode publique : addition avec un objet de même classe 32 (define/public (ajout o) 33 (ajout_x (send o get_x)) 34 (ajout_y (send o get_y))) 35 36 ; méthode publique : affiche les attributs de l’objet 37 (define/public (affiche) 38 (display 39 (string-append "x = " (number->string x) " y = " (number->string y)))))) 40 41 ; classefille hérite de maclasse 42 (define classefille% 43 (class maclasse% 44 (super-new) 45 ; surcharge de la méthode affiche 46 (define/override (affiche) 47 (display 48 (string-append "x : " 49 (number->string (send this get_x)) 50 "n" 51 "y : " 52 (number->string (send this get_y))))))) 53 54 ; création d’un objet de classe maclasse 55 (define o_maclasse (new maclasse% [init_x 10] [init_y 20])) 56 ; création d’un objet de classe classefille 57 (define o_fille (new classefille% [init_x 8] [init_y 9])) Un exemple d’utilisation du code ci-dessus dans une session DrRacket :
  7. 7. 2.3. La programmation par contrats 7 La notion d’interface est également présente. Une classe peut indiquer qu’elle implémente une ou plusieurs interfaces dont les signatures sont définies via la fonction "interface". Une interface peut par ailleurs étendre d’autres interfaces. Il est possible d’utiliser les "mixins" afin d’agréger dans une classe donnée les attributs et méthodes d’autres classes sans passer par le mécanisme de l’héritage. Un concept similaire est également supporté avec les "traits" qui là aussi permettent d’importer des méthodes au sein d’une classe. Les "traits" offrent l’avantage supplémentaire de laisser au programmeur le soin de gérer explicitement les conflits de nommage. On peut ainsi notamment définir des alias de noms pour certaines méthodes ou bien en exclure d’autres. 2.3 La programmation par contrats C’est une méthode qui reprend l’image d’un contrat entre deux entités. Chaque partie prenante s’engage sur des obligations et des garanties. Dans un programme, cela se traduit typiquement par des contraintes sur les données en entrée et en sortie des fonctions développées. Racket permet de préciser ces contraintes au niveau de la définition d’un module [8]. En voici un exemple : 1 #lang racket/load 2 (module test_contrat racket 3 ; Le contrat précise : 4 ; - 1er argument de fonction doit vérifier test_arg? 5 ; - le résultat de fonction doit vérifier test_resultat? 6 (provide (contract-out [fonction (-> test_arg? test_resultat?)])) 7
  8. 8. 2.3. La programmation par contrats 8 8 ; fonctions qui vérifient les contraintes du contrat 9 (define test_arg? number?) 10 (define (test_resultat? v) (equal? 42 v)) 11 12 ; une fonction qui attend un nombre en paramètre et renvoie 42 13 (define (fonction v) 42)) 14 15 (module exemple_ok racket 16 (require ’test_contrat) 17 (display "Contrat respecté : n") 18 ; ok car contraintes du contrat respectées 19 (fonction 1)) 20 21 (module exemple_ko racket 22 (require ’test_contrat) 23 (display "Contrat non respecté : n") 24 ; ko car le paramètre est une chaîne de caractères 25 (fonction "X")) 26 27 (require ’exemple_ok) 28 (require ’exemple_ko) avec son exécution dans l’environnement DrRacket : A noter que l’exemple utilise "#lang racket/load" de manière à pouvoir définir plusieurs modules dans DrRacket.
  9. 9. 2.4. Les modules et les "units" 9 2.4 Les modules et les "units" Les modules [9] permettent de fournir des bibliothèques de fonctions réutili- sables. Un module est typiquement codé dans son propre fichier source. Il est nécessaire de préciser explicitement les fonctions exportées, et qui seront donc rendues disponibles pour d’autres modules. Des modules peuvent être regroupés dans une collection ce qui permet de les utiliser sans passer direc- tement par le chemin vers le fichier correspondant. Racket permet également de télécharger un module disponible sur le serveur PLaneT 1 qui centralise ceux mis à disposition par la communauté. Les "units" [10] (que l’on pourrait traduire par unités de compilation) per- mettent d’organiser un programme en composants réutilisables et séparément compilables. L’interface d’un "unit" est décrite en terme de signature qui explicite les fonctions et leurs types. Il devient ainsi possible de compiler un programme utilisant un "unit" dont seule la signature sera connue et dont l’implémentation sera chargée dynamiquement à l’exécution [11]. 1. http://planet.racket-lang.org/
  10. 10. Chapitre 3 Fonctions graphiques DrRacket propose nativement plusieurs bibliothèques de fonctions gra- phiques. Nous allons en voir trois exemples. Mais d’autres librairies sont disponibles comme Sgl [12] qui permet d’accéder aux fonctions OpenGL pour les graphismes en trois dimensions et comme Racket Drawing Toolkit [13] qui offre une interface de programmation basée sur le modèle du langage Postscript. 3.1 Slideshow Slideshow [14] est une librairie dédiée à la création de présentation. Le concept se rapproche de la classe Beamer [15] pour LATEX. On crée un pro- gramme qui va décrire le document de présentation et produire en sortie un fichier PDF par exemple. Ainsi, le programme suivant : 1 #lang slideshow 2 ; c : cercle diamètre 20 pixels 3 (define c (circle 20)) 4 ; r : rectangle largeur 30 pixels / hauteur 20 pixels 5 (define r (rectangle 30 20)) 6 ; fonction dessine N rectangles 7 (define (rectangles largeur_depart fun_center) 8 (define (carre largeur) 9 (if (< largeur 5) 10 (rectangle 0 0) 11 (begin 12 (fun_center 13 (rectangle largeur largeur) 14 (carre (/ largeur 2)))))) 15 (carre largeur_depart)) 16 ; rectangles_hc : rectangles centrés horizontalement 17 (define (rectangles_hc) (rectangles 120 hc-append)) 10
  11. 11. 3.2. GUI 11 18 ; rectangles_vc : rectangles centrés verticalement 19 (define (rectangles_vc) (rectangles 120 vc-append)) 20 ; première page slide 21 (define slide1 22 (slide 23 #:title "Mon premier slide" 24 (text "Un peu de texte" null 24) 25 (rectangles_vc) 26 (arrow 20 31416/4000))) chargé et exécuté dans DrRacket affichera cette image : 3.2 GUI Racket Graphical Interface Toolkit [16] propose un ensemble de fonctions pour implémenter des interfaces graphiques utilisateurs avec fenêtres, bou- tons, menus... Par exemple, le programme suivant : 1 #lang racket/gui 2 (require racket/gui/base) 3 (require racket/path) 4 5 ; Création de la fenêtre 6 (define fenetre (new frame% [label "Ma fenêtre"] 7 [width 400] 8 [height 320]))
  12. 12. 3.2. GUI 12 9 10 ; Texte à l’intérieur de la fenêtre 11 (define message (new message% [parent fenetre] 12 [label "Cliquez sur le bouton !"] 13 [auto-resize #t])) 14 15 ; Premier bouton 16 (new button% [parent fenetre] 17 [label "Cliquez ici"] 18 ; on change le message si clic 19 (callback (lambda (button event) 20 (send message set-label "Merci d’avoir cliqué sur le bouton")))) 21 22 ; Affiche le chemin du fichier sélectionné 23 (define (affiche_chemin chemin) 24 (send message set-label (path->string chemin))) 25 26 ; Deuxième bouton 27 (new button% [parent fenetre] 28 [label "Sélectionner un fichier"] 29 ; sélecteur de fichier si clic 30 (callback (lambda (button event) 31 (affiche_chemin (get-file))))) 32 33 ; Editeur 34 (define canvas (new editor-canvas% [parent fenetre])) 35 (define editeur (new text%)) 36 (send canvas set-editor editeur) 37 38 ; On affiche la fenêtre 39 (send fenetre show #t) chargé et exécuté dans DrRacket affichera cette interface :
  13. 13. 3.3. PLoT 13 3.3 PLoT PLoT [17] permet de réaliser un programme qui va décrire un graphique et produire en sortie une image dans un des formats géré par DrRacket (PNG, PDF, Postscript ou SVG par exemple). De nombreux types de graphiques sont possibles comme les courbes, les nuages de points, les histogrammes, les toiles d’araignées et les surfaces en trois dimensions. Les fonctionnalités proposées se rapprochent de ce qu’il est possible de réaliser avec des programmes comme Graphics Layout Engine [18] ou bien encore Asymptote [19]. Par exemple, le programme suivant : 1 #lang racket 2 (require plot) 3 (define data_histo (list #("Jan." 100) #("Fév." 120) #("Mars" 139) 4 #("Avr." 130) #("Mai" 70) #("Juin" 90) 5 #("Jui." 210) #("Août" 220) #("Sept." 190) 6 #("Oct." 141) #("Nov." 215) #("Déc." 210))) 7 (define data_ligne (list (vector 0.5 110) (vector 1.5 150) (vector 2.5 100) 8 (vector 3.5 170) (vector 4.5 250) (vector 5.5 250) 9 (vector 6.5 210) (vector 7.5 280) (vector 8.5 300) 10 (vector 9.5 310) (vector 10.5 290) (vector 11.5 340))) 11 (plot (list (discrete-histogram data_histo 12 #:label "Réalisé") 13 (lines data_ligne 14 #:label "Objectif")) 15 #:width 600 16 #:height 500
  14. 14. 3.3. PLoT 14 17 #:y-max 500 18 #:x-label "Mois" 19 #:y-label "C.A. ventes") chargé et exécuté dans DrRacket affichera ce graphique :
  15. 15. Chapitre 4 Déboguage L’environnement DrRacket inclue un outil de déboguage [20] qui permet de dérouler pas à pas le programme et de visualiser le contenu des variables au fur et à mesure de l’exécution. On peut également placer à la souris des points d’arrêts sur le code source. Le déroulement du programme stoppera sur ces points d’arrêts ce qui permettra d’inspecter le contenu des variables à cet instant de l’exécution. L’utilisateur peut également modifier dynamiquement la valeur d’une va- riable ou bien la valeur de retour d’une fonction. Il suffit de placer le curseur de la souris sur la variable ou la fonction concernée et de faire un clic droit afin d’indiquer la nouvelle valeur. La suite de l’exécution du programme utilisera alors la valeur saisie. Le debugger permet aussi de visualiser la pile d’appel des fonctions. Si l’on clique sur un élément de cette pile, la liste des variables affichées sera mise à jour pour tenir compte de leurs portées par rapport à la position sélectionnée dans la pile. 15
  16. 16. Déboguage 16 Exemple Dans l’exemple ci-dessus, la session de déboguage montre que l’exécution du programme est arrêtée à la ligne où figure le triangle vert (ligne du "if"). On peut également voir la valeur des variables "acc" (une liste avec un seul élément), "nb" (de valeur 2) et "v" (qui contient une chaîne de caractères).
  17. 17. Chapitre 5 Extension de l’environnement 5.1 Les plugins Les plugins [21] permettent de modifier l’interface et/ou les fonctionnalités de DrRacket. Lors de son démarrage, DrRacket charge et exécute l’ensemble des plugins installés. Pour ajouter un nouveau plugin, il faut tout d’abord créer un dossier au niveau du répertoire nommé "collects". Ce répertoire est créé lors de l’instal- lation de DrRacket et contient déjà les nombreux plugins inclus par défaut. Nous allons prendre pour l’exemple un sous-répertoire que nous appellerons "monplugin". L’étape suivante consiste à créer dans ce répertoire "monplugin" un premier fichier nommé "info.rkt" : 1 #lang setup/infotab 2 (define drracket-name "Mon plugin") 3 (define drracket-tools (list (list "monplugin.rkt"))) C’est un programme Racket qui permet de préciser le nom du plugin ainsi que les fichiers sources qui vont implémenter les fonctions du plugin. Pour que ce nouveau plugin soit pris en compte lors du prochain démarrage de DrRacket, il peut être nécessaire de forcer la mise à jour du cache des fichiers "info.rkt" avec la commande "raco setup". Dans notre exemple, les fonctions du plugin sont codées au sein d’un seul fichier appelé "monplugin.rkt". Le programme contenu dans ce fichier définit un module qui implémente l’interface "tool@" définie par DrRacket : 1 #lang racket/gui 2 (require drracket/tool 3 racket/class 17
  18. 18. 5.1. Les plugins 18 4 racket/gui/base 5 racket/unit 6 mrlib/switchable-button 7 plot) 8 (provide tool@) 9 10 (define tool@ 11 (unit 12 (import drracket:tool^) 13 (export drracket:tool-exports^) 14 15 (define (affiche_graph g) 16 (define bmp (send g get-bitmap)) 17 (define fenetre (new frame% [label "Graphique"] 18 [width (send bmp get-width)] 19 [height (send bmp get-height)])) 20 (define c 21 (new canvas% 22 [paint-callback (lambda (c dc) (send dc draw-bitmap bmp 0 0))] 23 [parent fenetre])) 24 (send fenetre show #t)) 25 26 (define bt_affiche_graph 27 (mixin (drracket:unit:frame<%>) () 28 (super-new) 29 (inherit get-button-panel 30 get-definitions-text) 31 (inherit register-toolbar-button) 32 (let ((btn 33 (new switchable-button% 34 (label "Afficher le graphique") 35 (callback (lambda (button) 36 (affiche_graph 37 (plot 38 (function (lambda (x) (+ 3 x)) -5 +5 #:label "+ 3"))))) 39 (parent (get-button-panel)) 40 (bitmap icone)))) 41 (register-toolbar-button btn) 42 (send (get-button-panel) change-children 43 (lambda (l) 44 (cons btn (remq btn l))))))) 45 46 (define icone 47 (let* ((bmp (make-bitmap 16 16)) 48 (bdc (make-object bitmap-dc% bmp))) 49 (send bdc erase) 50 (send bdc set-smoothing ’smoothed) 51 (send bdc set-pen "black" 1 ’transparent) 52 (send bdc set-brush "blue" ’solid) 53 (send bdc draw-ellipse 2 2 8 8) 54 (send bdc set-bitmap #f) 55 bmp)) 56 57 ; inutilisés dans ce plugin mais doivent être malgré tout définis
  19. 19. 5.1. Les plugins 19 58 (define (phase1) (void)) 59 (define (phase2) (void)) 60 61 (drracket:get/extend:extend-unit-frame bt_affiche_graph))) Ce plugin d’exemple se contente d’ajouter un nouveau menu avec le titre "Afficher le graphique" dans la barre du haut de l’environnement DrRacket. Si l’utilisateur clique sur ce bouton, le traitement associé est exécuté. On affiche alors dans une nouvelle fenêtre ce graphique :
  20. 20. 5.2. Les macros 20 5.2 Les macros Racket supporte la création de macros [22] qui permettent de définir des transformations syntaxiques. C’est un moyen simple pour étendre le langage. Par exemple, ce programme : 1 #lang racket 2 ; définition de la macro affiche_dernier_element 3 (define-syntax affiche_dernier_element 4 (syntax-rules () 5 ; si un seul élément en paramètre, on affiche cet élément 6 [(affiche_dernier_element a) (display a)] 7 ; si deux éléments ou plus en paramètre 8 ; on appelle récursivement la macro avec tous les paramètres _sauf_ le premier 9 [(affiche_dernier_element a b ...) (affiche_dernier_element b ...)])) définit une macro nommée "affiche_dernier_élément". On peut appeler cette macro avec un ou plusieurs éléments en paramètre, elle affichera alors le tout dernier. La ligne 6 gère le cas où il n’existe qu’un seul élément en paramètre, la transformation syntaxique aboutit alors à la fonction d’affichage de ce paramètre. La ligne 9 gère le cas où au moins deux éléments existent. Dans ce cas, il y a appel récursif à la macro mais sans le premier paramètre lié ici à l’identifiant appelé "a". Voici un exemple d’utilisation de cette macro :
  21. 21. 5.3. Les langages 21 5.3 Les langages Dans les cas où l’utilisation des macros est insuffisante, Racket permet relativement simplement d’implémenter un nouveau langage [23]. L’idée est de pouvoir étendre le langage Racket avec de nouvelles syntaxes, voire de modifier des comportements déjà proposés par défaut pour le traitement du langage. Un exemple très simple est de définir un langage qui offre uniquement 4 pri- mitives pour réaliser les 4 opérations arithmétiques de base. Le code suivant définit un module (sauvegardé dans un fichier appelé "monlangage.rkt") qui pourra ensuite être utilisé comme langage : 1 #lang racket 2 3 (define-syntax-rule (add a b) (+ a b)) 4 (define-syntax-rule (min a b) (- a b)) 5 (define-syntax-rule (mul a b) (* a b)) 6 (define-syntax-rule (div a b) (/ a b)) 7 8 (provide #%top-interaction #%module-begin #%datum 9 add min mul div) On voit que les 4 primitives sont définies à l’aide de macros. Le module exporte ces 4 primitives ainsi que quelques autres qui proviennent du noyau de l’environnement DrRacket. Notamment #%top-interaction qui autorise l’utilisation de ce nouveau langage dans l’environnement interactif DrRacket. Et voici un exemple d’utilisation de ce module en tant que langage : La ligne "#lang s-exp ..." permet de lire le fichier "monlangage.rkt" en tant que module qui définit un langage puis de lire le code qui suit comme une s-expression (notation parenthésée du langage Scheme ou Lisp). Grâce à ce mécanisme, Racket permet par exemple d’implémenter un langage donné [24] ou de développer un langage dédié à un domaine précis (ou
  22. 22. 5.3. Les langages 22 DSL pour Domain Specific Language) comme l’implémentation d’un jeu d’aventure en mode texte [25]. Ce dernier exemple montre concrètement jusqu’à quel degré il est possible de définir le langage. On peut notamment forcer un ordre spécifique pour la définition des actions, des objets et des lieux du jeu 1. Il est ainsi possible de restreindre volontairement les capacités du nouveau langage et d’afficher un message explicite en cas d’erreur de syntaxe. Cet exemple montre également comment ajouter la notion de types au langage, utiliser une syntaxe différente de celle des s-expressions en mettant en place un lecteur syntaxique ad hoc 2 et enfin comment ajouter à l’environnement de développement DrRacket la coloration syntaxique pour le nouveau langage. 1. http://queue.acm.org/downloads/2011/racket/3-module-lang/world.rkt 2. http://queue.acm.org/downloads/2011/racket/5-lang/txtadv-reader.rkt
  23. 23. Chapitre 6 Conclusion Racket est un langage historiquement fonctionnel puisque très proche du Scheme. Il intègre d’autres paradgimes de programmation avec le modèle objets, la programmation par contrats, l’intégration du typage explicite ou bien encore la programmation logique. Racket permet également de produire un exécutable natif ce qui offre de bonnes performances 1. De nombreuses librairies sont présentes par défaut notamment pour le développement gra- phique et pour le développement d’applications web [26]. Au dessus du langage lui-même, l’environnement DrRacket simplifie la prise en main des fonctionnalités disponibles grâce à son interface graphique et à l’interactivité avec l’utilisateur qu’il permet. Malgré leur indéniable potentiel dans le développement d’applications, Dr- Racket et le langage Racket restent toutefois apparemment cantonnés au domaine de l’enseignement informatique. Leur usage dans un contexte pro- fessionnel semble en effet inexistant ou bien confidentiel. Même dans le développement d’applications libres, leur utilisation ne semble pas très po- pulaire. Le site web Ohloh 2, qui donne un ensemble de statistiques sur des projets dont le code source est disponible, indique pour décembre 2011 les données suivantes : Langage Nb. projets Nb. contributeurs Nb. lignes de code Racket 29 74 1 802 131 Scheme 2 102 3 616 18 309 308 Lisp 1 435 1 956 14 810 241 Objective Caml 903 1 715 16 296 749 Haskell 2 003 3 161 5 976 988 C 53 252 111 306 3 769 334 663 1. http://shootout.alioth.debian.org/ 2. http ://www.ohloh.net/ 23
  24. 24. Conclusion 24 On voit que l’utilisation du langage Scheme est relativement plus élevée par rapport à d’autres langages fonctionnels comme son ancêtre Lisp ou bien encore Haskell et Objective Caml. Mais Racket reste pour l’instant extrêmement minoritaire, en particulier si l’on se réfère au nombre de projets.
  25. 25. Références [1] Robert Bruce Findler and Jacob Matthews. The revised6 report on the algorithmic language scheme, 2011. http://www.r6rs.org/. [2] R6rs : Scheme, 2011. http://docs.racket-lang.org/r6rs/index.html. [3] The typed racket guide, 2011. http://docs.racket-lang.org/ ts-guide/index.html. [4] Datalog : Deductive database programming, 2011. http://docs. racket-lang.org/datalog/index.html. [5] Scribble : The racket documentation tool, 2011. http://docs. racket-lang.org/scribble/index.html. [6] Exceptions, 2011. http://docs.racket-lang.org/guide/exns.html. [7] Classes and objects, 2011. http://docs.racket-lang.org/guide/ classes.html. [8] Contracts, 2011. http://docs.racket-lang.org/guide/contracts. html. [9] Modules, 2011. http://docs.racket-lang.org/guide/modules.html. [10] Units (components), 2011. http://docs.racket-lang.org/guide/ units.html. [11] T. Stephen Strickland and Matthias Felleisen. Contracts for first-class modules. 2009. http://www.ccs.neu.edu/racket/pubs/dls09-sf.pdf. [12] Gl : 3-d graphics, 2011. http://docs.racket-lang.org/sgl/index. html. [13] The racket drawing toolkit, 2011. http://docs.racket-lang.org/draw/ index.html. [14] Slideshow : Figure and presentation tools, 2011. http://docs. racket-lang.org/slideshow/index.html. [15] Beamer, 2011. https://bitbucket.org/rivanvx/beamer/wiki/Home. 25
  26. 26. Références 26 [16] The racket graphical interface toolkit, 2011. http://docs.racket-lang. org/gui/index.html. [17] Plot : Graph plotting, 2011. http://docs.racket-lang.org/plot/ index.html. [18] Graphics layout engine, 2011. http://glx.sourceforge.net/. [19] Asymptote, 2011. http://asymptote.sourceforge.net/. [20] Graphical debugging interface, 2011. http://docs.racket-lang.org/ drracket/debugger.html. [21] Drracket plugins, 2011. http://docs.racket-lang.org/tools/index. html. [22] Macros, 2011. http://docs.racket-lang.org/guide/macros.html. [23] Creating languages, 2011. http://docs.racket-lang.org/guide/ languages.html. [24] Danny Yoo. F*dging up a racket. http://hashcollision.org/ brainfudge/. [25] Matthew Flatt. Creating languages in racket, 2011. http://queue.acm. org/detail.cfm?id=2068896. [26] Continue : Web applications in racket, 2011. http://docs.racket-lang. org/continue/. [27] Jean-Paul Roy. Premiers cours de programmation avec Scheme - Du fonctionnel pur aux objets avec DrRacket. Ellipses, 2010. http:// deptinfo.unice.fr/~roy/PCPS/, http://www.editions-ellipses.fr/ product_info.php?products_id=7515. [28] Matthias Felleisen. Racket is..., 2011. http://www.ccs.neu.edu/home/ matthias/Thoughts/Racket_is____.html. [29] Matt Might. 7 lines of code, 3 minutes : Implement a program- ming language from scratch, 2011. http://matt.might.net/articles/ implementing-a-programming-language/. [30] Sam Tobin-Hochstadt, Vincent St-Amour, Ryan Culpepper, Matthew Flatt, and Matthias Felleisen. Languages as li- braries. 2011. http://blog.racket-lang.org/2011/03/ languages-as-libraries-pldi-2011.html.

×