• Aucun résultat trouvé

Architecture et interactions des di erents agents respectant les

8.2 Modele de cooperation de GDRev

8.2.3 Architecture et interactions des di erents agents respectant les

Pour exprimer une notion d'ordre, une premiere idee consiste a utiliser l'operateur de sequentialite \:" a la place de l'operateur de parallelisme \," dans le corps de la re-qu^ete. Malheureusement, une telle formulation conduirait tres souvent a une situation de blocage. En e et, l'execution de B1 : B2 conduit a un blocage notamment si B1 se bloque. Ainsi, si par exemple l'evaluation de certaines proprietes par un agent sont dans un etat de blocage, il s'ensuit que l'agent suivant n'est pas execute. Par conse-quent, l'emploi de l'operateur de sequentialite est valide seulement dans les situations ou le premier agent execute reussit a construire entierement et tout seul la gure.

En fait, pour exprimer l'ordre d'execution des agents il s'agit de faire en sorte que l'execution d'un agent soit declenchee par son predecesseur une fois que celui-ci a e ectivement evalue l'ensemble3 des atomes de propriete decrivant la gure. Cette approche nous conduit au schema d'execution illustre par la gure 8.4.

Ce schema illustre le fait que l'agent lineaire relance ses buts en attente tant qu'il arrive a evaluer des contraintes. Une fois bloque, il (re)lance l'agent quadratique. Celui-ci relance l'agent lineaire s'il a su evaluer une contrainte, ou l'agent completion d'objets dans le cas contraire. D'une maniere similaire, l'agent completion d'objets relance l'agent lineaire s'il a su determiner une corde commune ou une mediatrice, ou l'agent intervalle sinon. En n, l'agent intervalle relance l'agent lineaire s'il a su instancier une variable, ou conduit a un succes.

Pour formaliser un tel mecanisme, nous associons a chaque agent une liste pourvue d'un suxe libre( FreesLinpour l'agent lineaire, FreesQuad pour l'agent quadratique,

FreesCptObjs pour l'agent completion d'objets, FreesInt pour l'agent intervalle). Ces listes sont regroupees dans une liste Frees. Elles ont un double r^ole. Elles permettent: 1. de gerer le processus de resolution en bloquant un agent, ou les buts d'un agent, en attente d'informations supplementaires sur le suxe libre de la liste lui cor-respondant dans l'argument Frees. Pour ce faire nous avons de ni le predicat

gelerAgent( Id, LProps, LObjs, Frees)ou l'argument Id est l'identi cateur de l'agent a geler.

Liberer un agent revient a speci er que la variable (le suxe libre) sur laquelle

3. Nous allons voir plus loin que ceci n'est pas tout a fait exact s'agissant des agents quadratique et completion d'objets.

8.2 Modele de cooperation de GDRev 151

Agent linéaire

Agent quadratique

Agent complétion d’objets

Agent intervalle

Fig. 8.4 { Schema de contr^ole des agents.

il est en attente d'informations supplementaires est une liste ayant au moins un element. Pour ce faire, nous avons de ni le predicat libererAgent( Id, Frees) ou l'argument Id est l'identi cateur de l'agent a liberer.

2. d'\espionner" l'ajout de contraintes au systeme de contraintes courant par un agent en examinant la valuation du dernier element de la liste lui correspon-dant. Si cet element est une variable, cela signi e que l'agent correspondant n'a pas pose de contraintes. Si cet element est instancie a la valeur 1, alors l'agent correspondant a reussi a poser une contrainte.

Pour marquer qu'un agent a reussi a poser une contrainte, nous avons de ni le predicat marquerTellContraintes( Id, Frees) ou l'argument Id est l'identi ca-teur de l'agent.

Pour determiner si un agent a (resp. n'a pas) reussi a poser une contrainte nous avons de ni le predicattellContraintes( Id, Frees)(resp.nonTellContraintes( Id,

Frees)) ou l'argument Id est l'identi cateur de l'agent \espionne".

Il reste le probleme de pouvoir determiner si un agent a e ectivement evalue tous les atomes de la liste des proprietes, dans la mesure ou l'evaluation d'un atome et le parcours des atomes de la liste des proprietes se fait en parallele. Pour resoudre ce probleme, une idee consiste a comptabiliser pour chaque agent d'une part les proprietes qu'il a evaluees, et d'autre part le nombre de ses appels recursifs. Un agent peut ^etre libere par son predecesseur (cf gure 8.4) si le nombre des proprietes evaluees par ce dernier correspond au nombre de ses appels recursifs avec la condition supplementaire que la liste des proprietes a evaluer est reduite a un suxe libre. Une maniere de de nir

152 Modele de cooperation

un compteur est de construire une liste pourvue d'un suxe libre et de considerer que le nombre d'elements de celle-ci correspond a la valeur du compteur de ni. Ainsi, pour comptabiliser d'une part le nombre des proprietes evaluees par un agent et d'autre part le nombre de ses appels recursifs, on construit deux listes de ce type appelees respectivementIn et Out.

agentLin(LProps, LObjs, In, Out, Frees):: gureNonConstruite(LObjs):

free(LProps):

conditionLiberation(In, Out)! etablirBilanLin(LObjs, Frees) agentLin(LProps, LObjs, In, Out, Frees)::

(Prop, SProps)^ know(LProps): tell(LProps = [Propj SProps]): marquerListe(Out):

(

evaluerAtomeLin(Prop, LObjs, In, Frees), agentLin(SProps, LObjs, In, Out, Frees) ) etablirBilanLin(LObjs, Frees):: estFigureConstruite(LObjs): terminerProcessus(Frees)! stop etablirBilanLin(LObjs, Frees):: estFigureNonConstruite(LObjs): tellContraintes(lin, Frees): libererAgent(lin, Frees)! etablirBilanLin(LObjs, Frees) etablirBilanLin(LObjs, Frees):: estFigureNonConstruite(LObjs): nonTellContraintes(lin, Frees): libererAgent(quad, Frees)! etablirBilanQuad(LObjs, Frees)

Tab.8.6 { Structure generale de l'agent lineairesous contr^ole.

La formalisation de cette idee est donnee pour l'agent lineaire dans le tableau 8.6. Le predicat conditionLiberation(In, Out), donne dans le tableau 8.7, est vrai si et seulement si les listes pourvues d'un suxe libreIn et Out ont le m^eme nombre

d'ele-8.2 Modele de cooperation de GDRev 153

ments. Le predicat marquerListe(L), illustre par le tableau 8.8, est vrai si le suxe libre de la liste L est une liste ayant au moins un element instancie a 1. Le predi-cat estFigureConstruite(LObjs) est vrai si et seulement si tous les objets de la gure contenus dans la liste LObjs sont construits. Inversement, le predicat estFigureNon-Construite(LObjs) est vrai si et seulement si il existe au moins un objet de la gure qui ne soit pas construit. En n, pour achever le processus de construction, nous conside-rons le predicatterminerProcessus(Frees) qui libere tous les processus en attente a n d'assurer une terminaison sans processus en attente.

conditionLiberation(In, Out):: free(Out) !stop

conditionLiberation(In, Out)::

(SOut, SIn)^(know(Out), know(In)) ! tell(Out = [ jSOut], In = [ jSIn]) !

conditionLiberation(SIn, SOut)

Tab. 8.7 {Condition de liberation de l'agent successeur.

On peut remarquer que cette formulation a conduit a ajouter a la clause evaluerA-tomeLin d'une part un argument In, c'est-a-dire un argument permettant de comp-tabiliser le nombre d'atomes evalues, et d'autre part l'argument Frees, c'est-a-dire la liste des listes de contr^ole des agents a n de (re)positionner en attente l'evaluation d'une contrainte pseudo-lineaire.

marquerListe(L):: free(L) ! tell(L = [1 j ])! stop marquerListe(L):: know(L) ! (SL)^ L = [1 j SL]! marquerListe(SL)

Tab. 8.8 { Clause marquerListe/1.

La formalisation du contr^ole de l'agent quadratique peut ^etre faite d'une maniere similaire a celle de l'agent lineaire. Toutefois, a n de reduire le nombre des racines

154 Modele de cooperation

carrees calculees, il est bloque une fois qu'il a evalue une contrainte quadratique. Ceci est realise gr^ace aux predicats decrits dans le tableau 8.9.

agentQuad(LProps, LObjs, In, Out, Frees):: free(LProps) !

libererAgent(cptObjs, Frees)

agentQuad(LProps, LObjs, In, Out, Frees):: (Prop, SProps)^ know(LProps):

tell(LProps = [Propj SProps]): marquerListe(Out):

(

evaluerAtomeQuad(Prop, LObjs, In, Frees),

poursuivreAgentQuad(SProps, LObjs, In, Out, Frees) )

poursuivreAgentQuad(LProps, LObjs, In, Out, Frees):: conditionLiberation(In, Out):

tellContraintes(quad, Frees): (

libererAgent(lin, Frees),

gelerAgent(quad, LProps, LObjs, In, Out, Frees) )

poursuivreAgentQuad(LProps, LObjs, In, Out, Frees):: conditionLiberation(In, Out):

nonTellContraintes(quad, Frees)!

agentQuad(LProps, LObjs, In, Out, Frees)

Tab. 8.9 { Structure generale de l'agent quadratique sous contr^ole.

Les cordes communes et/ou mediatrices de la gure peuvent ^etre recherchees et ajoutees une a une suivant un schema de contr^ole semblable a celui de l'agent quadra-tique ou une seule fois suivant un schema de contr^ole semblable a l'agent lineaire. A n de privilegier la rapidite de construction, nous avons choisi de les ajouter une a une. En e et, la complexite de l'algorithme de l'agent completion d'objets est en O(n2) ou

n est le nombre d'atomes de propriete de la gure. Ainsi, en les ajoutant une a une, on espere limiter ce co^ut.

En n, le schema de contr^ole de l'agent intervalle est semblable a celui de l'agent lineaire a la di erence qu'il ne libere aucun agent apres lui.

8.2 Modele de cooperation de GDRev 155

Il s'ensuit qu'une formulation du programme dans son ensemblesatisfaisant les pre-ferences etablies en matiere de construction peut ^etre celle decrite dans le tableau 8.10.

f

... Declarations des clauses.

.

(LProps, LObjs)^

tell(LProps = [...Speci cations des proprietes de la gure... j ]: tell(LObjs = [...Speci cations des objets de la gure... j ]! (FreeLin, InLin, OutLin,

FreeQuad, InQuad, OutQuad,

FreeCptObjs, InCptObjs, OutCptObjs, FreeInt, InInt, OutInt)^

tell(Frees = [FreesLin, FreesQuad, FreesCptObjs, FreesCptProps]): tell(FreesLin = [ j ])!

(

(FreesLin = [ j ]:

agentLin(LProps, LObjs, InLin, OutLin, Frees) ),

(FreesQuad = [ j ]:

agentQuad(LProps, LObjs, InQuad, OutQuad, Frees) ),

(FreesCptObjs = [ j ]:

agentCptObjs(LProps, LObjs, InCptObjs, OutCptObjs, Frees) ),

(FreesInt = [ j ]:

agentInt(LProps, LObjs, InInt, OutInt, Frees) )

) g

Tab. 8.10 { Architecture generale du programme de resolution de contraintes geometriques sous contr^ole.

On note que dans cette formulation seule l'execution de l'agent lineaire (la clause

agentLin) est \gardee" par une contrainte qui peut ^etre impliquee par le store. Il s'en deduit que cet agent est le seul agent qui puisse ^etre execute. Une fois son execution terminee, celui-ci libere l'agent quadratique au travers de la variable FreesQuad, qui lui delivre l'agent completion d'objets en speci ant que la variable FreesCptObjs est une liste contenant au moins un element. En n, ce dernier libere l'agent intervalle au travers de la variable FreesInt.

156 Modele de cooperation

De la sorte, on aboutit a une formulation respectant les preferences etablies, dans laquelle la rapidite de construction est privilegiee vis a vis de la complexitede la gure en terme du nombre de racines carrees calculees.

Avant de modeliser les di erents agents et leurs interactions, nous introduisons le predicat tres utile indexObjet. Il permet de retrouver l'index d'un objet dans la liste des objets a partir de son identi cateur. Sa speci cation est telle que indexObjet(Id, LObjs, Index) est veri e si et seulement si Index est l'index de l'objet identi e parId

dans la liste des objets LObjs.