• Aucun résultat trouvé

6.3 G´ en´ eration des substitutions B

6.3.2 G´ en´ eration des op´ erations

6.3.2.2 Analyse des clauses d’entr´ ee

Lorsque l’expression uj d’une clause d’entr´ee de la liste IC (bF, aF) est un terme fonctionnel, alors sa traduction en B est simple. Si l’expression uj est un terme conditionnel, alors il faut analyser les diff´erentes conditions sp´ecifi´ees dans les pr´edicats des parties if. Intuitivement, le but de l’analyse est de retrouver quelles sont les valeurs de cl´e concern´ees par l’ex´ecution de l’action aF. Ainsi, lorsqu’un nouvel ´ev´enement de l’action aF est re¸cu par le syst`eme, on cherche `a d´eterminer les valeurs {−→v } telles que : b

F(t :: aF, −→v ) 6= b

F(t , −→v ). D’autre part, les pr´edicats if des termes conditionnels peuvent aussi inclure des contraintes qui ne portent pas sur la cl´e de l’attribut, mais sur les valeurs des param`etres du nouvel ´ev´enement. Ces contraintes sont appel´ees dans la suite des hypoth`eses.

Nous utilisons un arbre binaire appel´e arbre de d´ecision pour analyser les pr´edicats des termes conditionnels. Par exemple, le terme associ´e `a la clause TransferF(bIdI, mIdI0, ) dans la d´efinition de nbLoansF comprend deux expres-sions if then else end imbriqu´ees :

nbLoansF(s : T (main), mId : memberKey SetF) : N = match last (s) with

.. .

TransferF(bIdI, mIdI0, ) : if mId = mIdI0

then nbLoansF(front (s), mId ) + 1 else if mId = borrowerF(front (s), bIdI)

then nbLoansF(front (s), mId ) − 1 end

end, ..

.

Le filtrage ne permet pas de d´eterminer la valeur de la variable cl´e mId de nbLoansF. Les conditions dans les parties if caract´erisent deux valeurs possibles pour mId . L’expression nbLoansF(front (s), mId )+1 est associ´ee `a la valeur de cl´e mId = mIdI0, alors que l’expression nbLoansF(front (s), mId )−1 correspond `

le membre qui re¸coit le transfert ( mId = mIdI0 ) voit son nombre de prˆets augment´e d’une unit´e, alors que l’emprunteur du livre bIdI avant le transfert ( mId = borrowerF(front (s), bIdI) ) voit son nombre de prˆets diminu´e d’une unit´e. La construction et l’analyse des arbres de d´ecision sont d´etaill´ees dans le paragraphe “Arbres de d´ecision” ci-dessous.

L’algorithme consiste essentiellement `a identifier les valeurs de cl´e affect´ees par chaque action et les hypoth`eses sous lesquelles l’action peut ˆetre ex´ecut´ee. Afin de consid´erer tous les cas possibles, l’analyse de chaque clause d’entr´ee aF(−p

jI) : uj de la liste IC (bF, aF) g´en`ere :

– une substitution θuj qui relie chaque param`etre actuel de la clause aF(−p

jI) `

a un param`etre formel de l’action aF de la sp´ecification eb3, – une conjonction d’hypoth`eses Huj sous laquelle uj est valide. Les paragraphes suivants d´ecrivent comment sont calcul´es θuj et Huj. Filtrage et hypoth`eses. Soit aF(−p

jI) une clause d’entr´ee de IC (bF, aF). L’analyse d´ecrite dans ce paragraphe est commune `a toutes les clauses d’entr´ee, que le terme associ´e soit fonctionnel ou conditionnel. L’objectif est d’identifier les param`etres actuels de la clause aF(p1I, . . . , pmI) avec les param`etres formels de l’action aF(p1F, . . . , pmF), dans le but de retrouver pour quelles valeurs de −→

pF l’action aF peut ˆetre ex´ecut´ee :

∃ var (p1I, . . . , pmI) • ^

l

plI = plF

On peut alors d´eterminer les variables du terme associ´e uj en fonction des pa-ram`etres formels de aF. Au d´ebut de l’analyse, le pr´edicat Huj est true et la sub-stitution θuj est vide. Ensuite, pour chaque param`etre plI de la clause d’entr´ee, il y a trois cas `a consid´erer :

1. Si plI est le symbole “ ”, alors le terme uj est valide pour chaque valeur possible du param`etre plF. θuj et Huj restent inchang´es.

2. Si plI est une constante c, alors le terme uj est valide uniquement lorsque plF = c. La condition plF = c est alors ajout´ee en conjonction `a l’hypoth`ese Huj. La substitution θuj reste inchang´ee.

3. Si plI est une variable v , alors le param`etre plI est associ´e au param`etre formel plF et la substitution plI := plF est ajout´ee dans θuj. De plus, si cette variable v apparaˆıt `a plusieurs reprises dans l’ensemble des param`etres p1I, . . . , pmI, alors il faut v´erifier que les param`etres correspondants dans p1F, . . . , pmF sont les mˆemes. Formellement, soit Jv la liste des indices des param`etres p1I, . . . , pmI o`u v apparaˆıt, alors pour chaque i ∈ Jv, la substitution plI := plF doit appartenir `a θuj et la conditionV

i1,i2∈Jv(pi1F = pi2F) est ajout´ee dans Huj.

Par exemple, prenons le cas de la clause TransferF(bIdI, mIdI0, ) dans la d´efinition de nbLoansF. Par l’analyse d´ecrite ci-dessus, on obtient :

θuj = {bIdI := bIdF, mIdI0 := mIdF} Huj = true

S’il existe des hypoth`eses sur les param`etres, comme dans le cas des clauses d’entr´ee LendF dans la d´efinition d’attribut dueDateF :

6.3. G ´EN ´ERATION DES SUBSTITUTIONS B 111 dueDateF(s : T (main), bId : bookKey SetF) : DATE =

match last (s) with ..

.

LendF(bIdI, , Permanent ) : CurrentDateF+365, LendF(bIdI, mIdI, Classic) : CurrentDateF

+loanDurationF(front (s), mIdI), ..

.

alors les r´esultats de l’analyse sont respectivement pour la premi`ere et pour la deuxi`eme clause :

θu1 = {bIdI := bIdF} Hu1 = (typeF = Permanent )

θu2 = {bIdI := bIdF, mIdI := mIdF} Hu2 = (typeF = Classic)

En r´esum´e, les substitutions θuj permettent de faire le lien entre les variables utilis´ees dans la clause d’entr´ee et les param`etres formels de l’action aF. Comme les signatures (`a l’exception du param`etre resB) de aB et aF sont les mˆemes, chaque param`etre de l’action eb3est identifi´e au param`etre correspondant dans l’op´eration B. Par cons´equent, nous consid´erons dans la suite que, par exten-sion, θuj fait le lien entre les variables utilis´ees dans les clauses d’entr´ee et les param`etres formels des op´erations B `a g´en´erer.

Arbres de d´ecision. La principale difficult´e dans le processus de traduction concerne l’analyse des termes conditionnels. En effet, pour une mˆeme clause d’entr´ee, plusieurs valeurs de cl´e peuvent ˆetre affect´ees et les pr´edicats if peuvent aussi inclure des hypoth`eses sur les param`etres de l’´ev´enement. Afin d’analy-ser les diff´erentes conditions des termes conditionnels, nous utilisons des arbres binaires, appel´es arbres de d´ecision. Dans la suite, l’application de la substitu-tion θ au terme u est not´ee par l’expression “u θ” ; elle est d´efinie comme le remplacement, pour chaque expression de la forme x := y dans θ, de toutes les occurrences de x dans u par y.

Rappelons que seules des d´efinitions d’attributs non cl´e peuvent inclure des termes conditionnels (voir section4.2.1). Soit bF une d´efinition d’attribut non cl´e de B (aF). Pour chaque clause d’entr´ee aF(−p

jI) : uj de la liste IC (bF, aF), on calcule tout d’abord θuj et Huj. Ensuite, l’arbre de d´ecision associ´e `a bF est construit en deux temps.

Dans un premier temps, la racine de l’arbre est bF et les feuilles corres-pondent aux diff´erentes clauses d’entr´ee aF(−p

jI) : uj de IC (bF, aF). Pour conser-ver la forme binaire de l’arbre, la construction est r´ealis´ee de la mani`ere suivante. Le nombre n de niveaux dans l’arbre est le nombre de clauses d’entr´ee dans IC (bF, aF). Le fils gauche de la racine est u1 θu1 et la branche correspondante est ´etiquet´ee par Hu1. Le fils droit de la racine est soit le sous-arbre g´en´er´e au niveau suivant, soit l’appel r´ecursif bF(front (s),−→

kF) s’il n’y a qu’une seule clause d’entr´ee. La branche vers le fils droit est ´etiquet´ee par ¬Hu1. Les sous-arbres

Hu 1 Hu 1 Hu 2 Hu 2 Hu n Hu n u u n n u F b 1 2 2 b (front(s),k) F 1

Fig. 6.2 – Premi`ere ´etape de la construction de l’arbre de d´ecision de bF

u

θu θu mId = borrower( bId )B

true false

nbLoans

( nbLoans (front(s), mId ) + 1 )

( nbLoans (front(s), mId ) − 1 )

mId = mIdB nbLoans (front(s),mId )F

F

nbLoans (front(s),mId ) ( mId = mId )

( mId = borrower( bId ) )B

B F

F F

Fig. 6.3 – Arbre de d´ecision g´en´er´e pour la clause TransferF de nbLoansF

sont g´en´er´es de la mani`ere suivante. Au niveau j −1 6= n, le fils gauche est uj θuj

avec une branche ´etiquet´ee par Huj et le fils droit est le sous-arbre de niveau j avec une branche ´etiquet´ee par ¬Huj. Au niveau n, le sous-arbre est simplement la feuille bF(front (s),−→

kF). Cette construction est illustr´ee par la figure6.2. Dans un deuxi`eme temps, chaque feuille de la forme uj θuj, o`u ujest un terme conditionnel, est remplac´ee par un sous-arbre dont les feuilles ne contiennent que des termes fonctionnels. Le sous-arbre de d´ecision g´en´er´e pour un terme condi-tionnel uj est de la forme suivante. La racine est uj θuj. Les fils de chaque nœud sont respectivement les parties then et else du terme conditionnel consid´er´e, avec comme ´etiquettes respectives sur les branches les conditions c et ¬c, o`u c est la condition de la partie if. Le processus est r´eit´er´e sur les parties then tant que toutes les feuilles de l’arbre ne sont pas des termes fonctionnels. Par exemple, dans le cas de la clause TransferF de la d´efinition d’attribut nbLoansF, on obtient l’arbre de d´ecision d´ecrit dans la figure6.3.