Rappel Ralf Treinen Université Paris Diderot UFR Informatique Laboratoire Preuves, Programmes et Systèmes treinen@pps.univ-paris-diderot.fr 6 mai 2015 Jusqu'à maintenant : un petit langage de programmation impératif Deux types : integer et boolean Expressions avec des opérateurs arithmétiques et logiques Déclaration des variables avec leur type au début du programme Instructions d'achage et d'aectation Instructions composées : boucle while... do... od, conditionnelle if... then... else...fi c Ralf Treinen 2015 Exemple d'un programme v a r x : i n t e g e r ; y : i n t e g e r ; b : b o o l e a n ; c : b o o l e a n ; b e g i n x := 7 3 ; i f b&&c! b t h e n p r i n t 42+1 x+y ; y := 4 2 ; e l s e y := x+x ; f i ; w h i l e 42>41 do p r i n t 7 3 ; od ; end Un langage avec des déclaration locales Extension du langage : déclarations locales On veux maintenant aussi permettre des déclarations de variables avec portée limitée. Pour cela il y a une décision fondamentale à prendre : est-ce qu'on veut permettre une redéclaration locale d'une variable?
Exemple : variable locale 1 v a r 2 x : i n t e g e r ; 3 y : i n t e g e r ; 5 x := 7 3 ; 6 y := x +42; 7 v a r 8 z : i n t e g e r ; 9 b e g i n 10 z := x + y ; 11 p r i n t ( z ) ; 12 end ; 13 p r i n t ( x+y ) ; 14 end Exemple : redéclaration d'une variable 1 v a r 2 x : i n t e g e r ; 3 y : i n t e g e r ; 5 x := 7 3 ; 6 y := x +42; 7 v a r 8 x : b o o l e a n ; 9 b e g i n 10 x := y >17; 11 i f x t h e n p r i n t ( 1 ) ; e l s e p r i n t ( 2 ) ; f i ; 12 end ; 13 p r i n t ( x+y ) ; 14 end Java : redéclaration pas autorisée Redéclaration de variables / E r r e u r de c o m p i l a t i o n / c l a s s Scope { } p u b l i c s t a t i c v o i d main ( S t r i n g [ ] a r g s ) { } i n t x = 4 2 ; { } i n t x = 7 3 ; En Java : la redéclaration d'une variable dans un bloc n'est pas permise (erreur de compilation). Il y a des autres langages de programmation qui admettent des redéclaration locales de variable. Les redéclaration sont aussi pertinentes pour l'implémentation de procédures qui peuvent accéder à des variables globales. Pour cette raison nous allons étudier les deux solutions.
Extension de la syntaxe abstraite Petite modication de la sémantique L'ensemble DL des Listes de Déclarations est... L'ensemble IL des listes d'instructions est... L'ensemble I des Instructions en syntaxe abstraite est : si e E alors Print(e) I, si s Σ, e E alors Assign(s, e) I, si e E, il 1, il 2 IL alors Cond(e, il 1, il 2 ) I, si e E, il IL alors While(e, il) I, si dl DL et il IL alors Bloc(dl, il) I. Jusqu'à maintenant, une variable n'a pas reçu une valeur initiale au moment de la déclaration. Modication : au moment de la déclaration, la variable reçoit une valeur initiale (0 pour les entiers, false pour les booléens). Raison : simplication technique. On aurait aussi pu étendre la syntaxe abstraite par une expression d'initialisation au moment de la déclaration d'une variable. Modication : exécution de déclarations Modication : exécution d'un programme Jugement dl Γ i, Γ b : l'exécution de la liste de déclarations dl crée un environnement entier Γ i, et un environnement booléen Γ b. Règles : DeclNil, Jugement Γ i, Γ b il Γ, i Γ : l'exécution de la liste b d'instructions il dans un environnement initial Γ i, Γ b donne un nouvel environnement Γ, i Γ b Règle modiée pour un programme complèt : dl Γ i, Γ b dl Γ i, Γ b Γ i, Γ b il Γ i, Γ b DeclSeq(Decl(s, int), dl) Γ i [s 0], Γ b Prog(dl, il) Γ i, Γ b dl Γ i, Γ b DeclSeq(Decl(s, bool), dl) Γ i, Γ b [s false]
À la Java : pas de redéclaration de variables À la Java : pas de redéclaration de variables Deux opérations sur les environnements Typage pour les blocs Union disjointe : si Γ 1 et Γ 2 sont deux environnements (de typage ou de valeur) avec des domaines disjoints, alors Γ 1 Γ 2 est déni comme { Γ1 (x) si x domaine(γ (Γ 1 Γ 2 )(x) = 1 ) Γ 2 (x) sinon Restriction : si Γ est un environnement, et D domaine(γ), alors la restriction de Γ à D est déni comme { Γ(x) si x D Γ D (x) = non-déni sinon Rappel des jugements de typage : Règle dl : Γ : la liste de déclarations dl donne lieu à l'environnement de typage Γ. Γ il : la liste d'instructions il est bien typée par rapport à l'environnement Γ. dl Γ Γ Γ : il Γ : Bloc(dl, il) À la Java : pas de redéclaration de variables Exécution des blocs Une modélisation plus complexe dl Γ, i Γ Γ b i Γ, Γ i b Γ il Γ, b i Γ b Γ i, Γ b Bloc(dl, il) Γ i domaine(γi ), Γ b domaine(γ b ) La technique des extensions et restrictions des environnements ne fonctionne plus dans le cas des redéclarations de variable. Raison : Une redéclaration d'une variable x masque, pour la durée d'exécution du bloc, une déclaration globale de x. Après avoir terminé le bloc, la variable x globale devient de nouveau visible. Nous avons donc maintenant besoin d'une liste d'environnements : quand on entre dans un bloc, un nouvel environnement est ajouté à la n de la liste ; quand on quitte un bloc, l'environnement le plus récent est supprimé.
Listes d'environnements Opérations sur les listes d'environnements Dans une liste d'environnements, l'environnement le plus globale ce trouve à gauche, et l'environnement le plus local se trouve à droite. Pour obtenir la valeur d'une variable, ou pour la modier, on parcourt la liste de droite à gauche : priorité à la déclaration la plus locale. Pour ne pas trop alourdir la notation nous ignorons maintenant la distinction entre environnement entier et environnement booléen. L'opération get permet de récupérer la valeur d'une variable : { Γn (s) si s domaine(γ get(s, (Γ 1,..., Γ n )) = n ) get(s, (Γ 1,..., Γ n 1 )) sinon L'opération set permet de modier la valeur d'une variable : { (Γ1,..., Γ set(s, v, (Γ 1,..., Γ n )) = n 1, Γ n [s v]) si s domaine(γ n ) set(s, v, (Γ 1,..., Γ n 1 )), Γ n sinon Règles à modier pour les listes d'environnements Nouvelle règle pour l'exécution d'un bloc Évaluation d'une variable Γ 1,..., Γ n Ident(s) get(s, (Γ 1,..., Γ n )) Aectation d'une variable dl Γ n+1 Γ 1,..., Γ n, Γ n+1 il Γ 1,..., Γ n, Γ n+1 Γ 1,..., Γ n Bloc(dl, il) Γ 1,..., Γ n Γ 1,..., Γ n e v Γ 1,..., Γ n Assign(s, e) set(s, v, (Γ 1,..., Γ n ))
Extension de la syntaxe Exemple : procédure Syntaxe concrète : dénition d'une procédure (à un argument) par proc nom(variable : type) bloc Syntaxe abstraite : dénition d'une procédure : nom de la procédure, nom du paramètre, type du paramètre, bloc. liste de dénitions de procédures :... bloc : liste de déclarations de variables, liste de dénitions de procédures, bloc. 1 v a r x : i n t e g e r ; 2 p r o c p ( y : i n t e g e r ) 3 v a r z : i n t e g e r ; 5 z := 2 y ; 6 p r i n t z ; 7 end 8 b e g i n 9 x := 5 ; 10 p ( x ) ; 11 end Exemple : procédure accédant à une variable globale 1 v a r x : i n t e g e r ; 2 p r o c p ( y : i n t e g e r ) 3 v a r z : i n t e g e r ; 5 z := 2 y ; 6 x := z ; 7 end 8 b e g i n 9 x := 5 ; 10 p ( x ) ; 11 p r i n t x ; 12 end Exemple : liaison statique ou dynamique 1 v a r x : i n t e g e r ; 2 p r o c p ( y : i n t e g e r ) 3 b e g i n 4 x := x+y ; 5 end 6 b e g i n 7 x := 1 ; 8 v a r x : i n t e g e r ; 9 b e g i n 10 x := 2 ; 11 p ( 1 ) ; 12 p r i n t x ; 13 end 14 end
Liaison statique ou dynamique Liaison en question : la connexion entre l'utilisation d'un nom (d'une variable, par ex.), et la déclaration du même nom. Problème : on peut avoir plusieurs déclarations du même nom, laquelle choisir? Liaison dynamique : la liaison est faite suivant la priorité à la déclaration la plus locale au moment de l'exécution. Liaison statique : la liaison est faite suivant la priorité à la déclaration la plus locale au moment de la dénition de la procédure. Tous les langages de programmation modernes suivent cette politique.