Informatique et recherche
opérationnelle
IFT2030

Concepts des langages de programmation

Automne 2002


Accueil

Professeur et
Démonstrateurs

Horaires et locaux

Notes de cours

Démonstrations
et devoirs

Examens

Liens utiles

Au sujet du
livre de cours

Consultez vos notes

Foire aux questions
(FAQ)

Démonstration 6: Introduction à Scheme

Note: Le "baratin" de la semaine est un sous-ensemble des notes de démonstrations du cours de Yoshua Bengio (http://www.iro.umontreal.ca/~bengioy/ift2030/A01/Demo1-scheme.htm)

Installation et utilisation de l'interprète

Toutes les informations relatives à l'interpréteur Gambit Scheme (Marc Feeley) sont dans le site http://www.iro.umontreal.ca/~gambit/ .
Vous trouverez  aussi des versions pour Mac, Windows et Unix.

a) Configuration sous Unix

Sous Unix, pour lancer l'interpréteur il suffit de tapez :

prompt% gsi
Gambit Version 3.0
>

  • Il est possible d'utiliser gambit à travers emacs aussi et donc de beneficier d'un environnement graphique. Pour plus de détails consultez  le site http://www.iro.umontreal.ca/~feeley/cours/ift2030/#scheme    section "Liens pour le langage Scheme".
  • Pour afficher toutes les options de l'interpréteur on utilise la commande ",?"

b) Documentation

Vous trouverez une documentation du langage Scheme dans le site http://www.schemers.org/Documents/Standards/R5RS/HTML/

c) Quelques exemples avec l'interpréteur

prompt% Gambit Version 3.0
> (display "Voici quelques exemples :\n")
Voici quelques exemples :
> (+ 3 2)
5
> (define (f x) (* 4 x))
> (f 2)
8
> (exit)
prompt%
> (define (f n) (let ((x 1) (y n)) (+ x y)))
> (f 3)
4
> (define s 4)
> s
4
> (define t (sqrt 2))
> t
1.4142135623730951
> (f t)
2.414213562373095
> (f s)
5

Types de données

 Les types de donnés que l'on retrouve dans scheme sont :
 

a)Les nombres

Scheme ne fait pas de distinction entre entier, ratiennel, réel ou complexe. Les entiers en scheme n'ont pas de limite de taille. Toute suite de chiffres, précédée ou non par le signe - est donc un entier valide avec représentation exacte.
    • Exemples de nombres entiers:
                              0    -1233324999238889230043    44
    • Exemple de rationels :
                                      1/2  123123345245234556245/2    3/4
    • Les réels en Scheme sont représentés de façon similaire aux double en C, donc ils sont inexacts. Exemples de nombres réels:
                                      1.0  -5.4e22    1e-10
    •    Exemples de nombres complexes :
                             2+i

b) Les contantes booléenes

Les constantes booléennes en Scheme sont notées:
                                   #t    #f

c) Les caractéres

        #\a         <=> le caractère 'a' en C
    #\(         <=> le caractère '(' en C
    #\space     <=> le caractère ' ' en C
    #\newline   <=> le caractère '\n' en C
 

d) Les chaînes de caractères

Les chaînes de caratères en Scheme sont représentés  texte entouré de guillemets.  Elles peuvent être formatées en utilisant le caractère le backslash "\". suivit  de caractères spéciaux tells que n ( retour à la ligne) t (tabulation)

> (define msg "Ceci est un titre \n \t Debut du paragraphe.\n")
> (display msg)
Ceci est un titre
         Debut du paragraphe.

 e) Les symboles

Les symboles sont représentés par un quote et une suite de cactères. Ils représentent une constante littérale.

> (define nom 'Marc)
> (define prenom 'Jean)
> (begin (display nom) #\t (display prenom) (newline))
MarcJean
 

Les expressions

Les expressions en Scheme sont soit une variable, une constante, un appel de fonction ou une forme spéciale.  Lorsque l'on évalue une liste, c'est un
appel de fonction qui est réalisé:

    (a b c) ; appel de la fonction a, avec b et c comme arguments.
        >(+ 1 2 3)
    6
    >(define (succ x) (+ x 1))
    >(succ 2)
    3

a) Variables et affectations

  • Pour définir des variables en Scheme, on peut utiliser la forme spéciale define :

  •     (define x 5)
      (define y "hello")
       (define z 'hello)

    On utilise l'apostrophe(quote) pour désigner un symbole.  Sans le quote, c'est l'évaluation de hello qui serait affecté à z, mais avec le quote, c'est le symbole hello. Les variables définies par define sont visible tout au long d'une session scheme.

Structures de contrôle

a) (  If (cond) expression1 expression2)

Exemple pour le if:
    >(define (f x) (if (< x 10)
                       (display "c'est petit!")
                       (display "c'est grand!")))
    >(f 3)
    c'est petit!
    >(f 25)
    c'est grand!

    En Scheme, tout ce qui n'est pas égal à #f est considéré vrai.
 

b) (begin expression1 expression2 ... expressionp)

Cette structure de contrôle permet de controler les effects de bord.

    >(begin (display "Premiere ligne.")
            (newline)
            (display "Deuxieme ligne."))
    Premiere ligne.
    Deuxieme ligne.
    >
 

   c) (cond  expression1 expression2... expressionp)

Cette commande est l'équivalent du case en C

       >(define (f x) (cond ((< x 5) (display "c'est petit!"))
                                  ((< x 15) (display "c'est moyen!"))
                         (else (display "c'est grand!"))))
    >(f 3)
    c'est petit!
    >(f 6)
    c'est moyen!
    >(f 25)
    c'est grand!
 

 les procédures AND, OR

  • La procédure and est utilisé comme suit :


    (and <exp1> <exp2> ... <expn>)

 Pour le and, on évalue les expressions de gauche à droite jusqu'à ce que l'on trouve une expression fausse(on retourne alors #f) ou que toutes les
expressions sont vraies(dans ce cas, on retourne la valeur de expn).

        >(and (= 2 2) (< 1 2))
    #t
    >(and (= 2 2) (< 1 2) (display "hello"))
    hello
    >(and (= 2 2) (> 1 2) (display "hello"))
    #f
    >(and)
    #t
 

  • La procédure or est utilisé comme suit :
           (or <exp1> <exp2> ... <expn>)
    Pour le or, on évalue les expressions de gauche à droite jusqu'à ce que l'on trouve une expression non-fausse(on retourne alors cette expression) ou que toutes les expressions sont fausses(dans ce cas, on retourne #f).

       >(or (= 2 2) (display "hello"))
    #t
    >(or (= 2 1) (display "hello"))
    hello
    >(or)
    #f

Quelques procédures intéressantes

a) Opérations sur les symboles

    Pour déterminer si une expression évalue à un symbole, on peut utiliser la fonction symbol? comme suit:

          (symbol? <expr>)

   Exemples:
    >(define abc 2)
    >(define x 'allo)
    >(symbol? abc)
    #f
    >(symbol? x)
    #t
    >(symbol? 'abc)
    #t

    En Scheme, il est possible de convertir les symboles en chaînes de caractères et vice-versa.  On utilise à cet effet les deux procédures suivantes:

    >(symbol->string 'abc)
    "abc"
    >(string->symbol "abc")
    abc
    >(string->symbol "a b c")
    |a b c|

Le dernier cas montre que certains caractères spéciaux ne pouvant normalement être contenus dans des symboles peuvent être utilisés.  Ceci n'est
pas conseillé puisque la façon de résoudre ce problème n'est pas nécessairement la même pour chaque implémentation de Scheme.  Avec Gambit, on
utilise le pipe pour délimiter les symboles contenant des caractères spéciaux.
 

b) Opération sur les procédures

D'abord, il convient de déclarer l'existance du prédicat procédure? qui détermine si une expression évalue à une procédure:

    >(procedure? +)
    #t
    >(define x 3)
    >(define (f x) (+ x 1))
    >(procedure? x)
    #f
    >(procedure? f)
    #t
    >(procedure? (lambda () 1))
    #t
 

c) les procédures de comparaisons eq? eqv? equal?

    La procédure eq? retourne #t seulement si <exp1> correspond au même objet que <exp2>.  Dans le cas des procédures ou des listes, le contenu n'est pas analysé. Pour les nombres et les caractères, il faut utiliser eqv?.

                (eq? <exp1> <exp2>)

    (eq? 'a 'a)                    ; #t
    (eq? '() '())                  ; #t
    (eq? 2 2)                      ; dépend du compilateur
    (eq? (list 1 2) (list 1 2))    ; #f
  • La procédure eqv? retourne la même chose que la procédure eq?, sauf que si les deux arguments sont des caractères ou des nombres, il retournera #t si les deux sont égaux.
  • La procédure equal? retourne vrai seulement si les deux expressions évaluent à un objet identique.  Cette procédure vérifiera notamment le contenu des listes pour savoir si elles sont équivalentes et ne se contentera pas de comparer les pointeurs comme eq? ou eqv?.
                     (equal? <exp1> <exp2>)

        (equal? 'a 'a)                    ; #t
    (equal? '() '())                  ; #t
    (equal? 2 2)                      ; #t
    (equal? (list 1 2) (list 1 2))    ; #t
    (equal? "abc" "abc")              ; #t
 

Entrées / Sorties

a) Affichage d'expression:

    >(define x (+ 2 3))
    >(display "Bonjour a vous!")
    Bonjour a vous!
    >(display x)
    5
    >(newline)    ; affiche un newline
 

b)  Saisie d'expression:

    >(define y (read))  ; On suppose que l'utilisateur tape (+ 1 2) ici.
    >y

    (+ 1 2)
 

Ecrire un script et Scheme

Pour charger un programme Scheme dans Gambit, utilisez la fonction load:
    (load "fichier.scm")
La commande load lira le fichier donné et interprétera chaque expression contenue dans celui-ci.
 
 

Travail pratique (pas noté mais fortement recommandé)

Manipulations des éléments de base

  • A) Écrire un programme qui demande à l'utilisateur de saisir son nom et qui affiche à l'écran un message de bienvenue.
  • B) Combien valent les expressions suivantes (ne vous aidez pas de l'interpréteur pour répondre):
    • (+ (- 4 3) (* (2 3) 5))
    • (+ 4/2 1/3)
    • (/ 4/2 1/3)
    • (not #f)
  • C) Pour chacuns des éléments suivants, indiquez leur nature (parmi chaîne, symbole, nombre, liste):
    • 'toto
    • '(1 2 3 4)
    • "abricot"
    • 123
    Que retourne Scheme lorsque vous tapez ces items ?
  • D) Que retourne Scheme dans les cas suivants:
    • (define f 15)
      f
      
    • (equal? '(1 2 (3 4)) '(1 2 (3 4)))
      (eq? '(1 2 (3 4)) '(1 2 (3 4)))
      
  • E) Simplifiez au maximum les instructions suivantes (a et b sont des booléens). Vérifiez vos réponses en utilisant l'interpréteur Scheme.
    • (and (< 1 2) (< 3 4))
    • (or (not a) (and a b))

    Ces deux expressions sont-elles équivalentes ? Vérifiez le avec Scheme.

    (or (and a b) (and (not a) (not b)))
    (not (or (and b (not a)) (and (not b) a)))
    
[top]


Dernière mise à jour : Thu Oct 24 16:12:56 EDT 2002
dift2030@iro.umontreal.ca