Vous êtes sur la page 1sur 119

Intelligence Artificielle Programmation en Logique

Programmation en Logique
Intelligence Artificielle Programmation en Logique

Classes de langage

 Langages impératifs
 séquencement des calculs spécifié
– contrôle total du flot d’exécution
 objets du langage diversifiés
– syntaxe riche (lourde :-))
 exemples : Pascal, C, C+, C++, Java, …
 Langages fonctionnels
 tout est fonction
– syntaxe dépouillée
– base mathématique forte : -calcul
 contrôle délégué à l’interprète
– utilisation intensive de la récursivité
 exemples : Lisp, Scheme, Haskell, …
Intelligence Artificielle Programmation en Logique

Une autre classe

 PROgrammation en LOGique
 tout est logique
– syntaxe simple et dépouillée
– base théorique : calcul des prédicats
 encore plus de contrôle donné à la machine
– récursion
– non déterminisme
 exemple : Prolog
Intelligence Artificielle Programmation en Logique

Logique

1. Calcul propositionnel
2. Calcul des prédicats
Intelligence Artificielle Programmation en Logique

1. Calcul propositionnel

 Comment écrire les formules ?


 Aspects syntaxiques

 Comment déterminer la valeur de vérité d’une


formule ?
 Aspects sémantiques

 Comment démontrer de nouveaux résultats ?


 Aspects déductifs
Calcul propositionnel
Intelligence Artificielle Programmation en Logique

Syntaxe d’une formule

 Données
 un ensemble P de variables propositionnelles
P = { p, q, r, … } énoncés élémentaires
 un ensemble C de connecteurs
C={,,,,}
 Formules
 p est une formule si p  P
  (H) est une formule si H est une formule
 (H)  (K) est une formule si H et K sont des formules et si
 C
H=(p  q), K=(r  s), H  K, H  K, …..
 Règles de suppression des parenthèses
Calcul propositionnel
Intelligence Artificielle Programmation en Logique

Sémantique d’une formule

 Logique bi-valuée
 faux (0)
 vrai (1)

 Notion d’interprétation
 donner une valeur de vérité à une variable
 ( p)   0 , 1 
 extension à un opérateur
 extension à une formule
Calcul propositionnel
Intelligence Artificielle Programmation en Logique

Tables de vérité : opérateurs

p p  0 1  0 1
0 1 0 0 0 0 0 1
1 0 1 0 1 1 1 1

 0 1  0 1
0 1 1 0 1 0
1 0 1 1 0 1
Calcul propositionnel
Intelligence Artificielle Programmation en Logique

Formules particulières

 Tautologies : formules toujours vraies


 La table de vérité ne contient que des 1
 exemple : p   p

p ( p) (p   p)  0 1
0 1 1 0 0 1
1 0 1 1 1 1
Calcul propositionnel

? ( p  q)  (p  q)

F  ( p  q )  (p  q)

p q ¬p ¬q pq ¬(pq) (¬ p  ¬ q) F

0 0 1 1 0 1 1 1
0 1 1 0 0 1 1 1
1 0 0 1 0 1 1 1
1 1 0 0 1 0 0 1

 0 1  0 1  0 1
0 0 0 0 0 1 0 1 0
1 0 1 1 1 1 1 0 1
Calcul propositionnel
Intelligence Artificielle Programmation en Logique

Catégories de formules

 Tautologies : formules toujours vraies

 Formules inconsistantes
 formules toujours fausses
 la table de vérité ne contient que des 0
 exemple : p   p

 Formules consistantes
 formules non toujours fausses

 ,  ( F )  1
Calcul propositionnel
Intelligence Artificielle Programmation en Logique

Formules particulières

 Formules tautologiquement équivalentes


 les tables de vérité sont les mêmes

 ,  ( F )   ( H )

 Condition nécessaire et suffisante :

(F)  (H) est une tautologie (F)  (H)


Calcul propositionnel
Intelligence Artificielle Programmation en Logique

Quelques équivalences utiles

F G  tauto ( F  G )  (G  F ) F  G  tauto F  G
F G  tauto GF F G  tauto GF
F  F  tauto 1 F  F  tauto 0

F   tauto F ( F  G )  tauto F  G


( F  G )  tauto F  G
 Propriétés de  et  lois de De Morgan
 associativité
 distributivité (dans les 2 sens)
 éléments neutres (0 pour  et 1 pour )
 éléments absorbants (1 pour  et 0 pour )
Calcul propositionnel
Intelligence Artificielle Programmation en Logique

Formes normales

 But avoir une représentation uniforme des


formules du calcul propositionnel
 limiter le nombre de connecteurs différents utilisés
 limiter l’allure des formules rencontrées
Calcul propositionnel
Intelligence Artificielle Programmation en Logique

Formes normales


Une formule F est dite sous forme normale disjonctive ssi
F est une disjonction de conjonctions de variables
propositionnelles et de leur négation

Toute formule du calcul propositionnel est tautologiquement


équivalente à une formule sous forme normale disjonctive


Une formule F est dite sous forme normale conjonctive ssi
F est une conjonction de disjonctions de variables
propositionnelles et de leur négation

Toute formule du calcul propositionnel est tautologiquement


équivalente à une formule sous forme normale conjonctive
Intelligence Artificielle Programmation Logique

Exemples de mise en forme normale conjonctive

(p  q) v (r  s) :

1.((p  q) v r)  ((p  q) v s)
2.( p v r)  ( q v r)  ((p  q) v s)
3.( p v r)  ( q v r)  ( p v s)  ( q v s)

Remarquer la croissance de la longueur de la formule qui résulte de l'application


de la loi de De Morgan

(p -> q) -> p :

1.(~p v q) -> p
2.~(~p v q) v p
3.(~~p  ~q) v p
4.( p  ~q) v p
5.(p v p)  (~q v p)
Calcul propositionnel
Intelligence Artificielle Programmation en Logique

Aspects déductifs

 notion de conséquence logique


 notion de démonstration
 notion de règles de déduction
Calcul propositionnel
Intelligence Artificielle Programmation en Logique

Conséquence logique

 Soit A = {F1, …, Fn} un ensemble de n formules

A G ssi (F1  …  Fn)  G

 Notion de réfutation
 démonstration par l’absurde

A G ssi F 1  …  Fn   G est
inconsistante
Calcul propositionnel
Intelligence Artificielle Programmation en Logique

Système formel

 Données
 un ensemble V de symboles
 un ensemble F de formules (F  V*)
 un ensemble A d’axiomes (A  F)
 un ensemble fini de règles de déduction
 Une démonstration dans un système formel S est
une suite d’énoncés A1, … An telle que :
 pour tout i, Ai est un axiome de S ou une conséquence
des énoncés précédents par application d’une des règles de
déduction
 Un théorème de S est le dernier énoncé d’une
démonstration
Calcul propositionnel
Intelligence Artificielle Programmation en Logique

Énoncé déductible

 Soit J un ensemble de formules


 Un énoncé A est dit déductible sous les
hypothèses J (noté J A) ssi
 il existe une suite finie A1, …, An d’énoncés telle que
– An = A
– pour tout i
 A est un axiome
i

 ou Ai  J
 ou Ai découle d’énoncés précédents par application
d’une règle d’inférence
Calcul propositionnel
Intelligence Artificielle Programmation en Logique

Quelques règles de déduction


classiques

 modus ponens
 p, p  q q

 modus tollens
 p q,  q p

 syllogisme
 p q, q r p r
Calcul propositionnel
Intelligence Artificielle Programmation en Logique

Propriétés d’un système formel

 Un système formel est correct ssi

si A alors A

 tout ce qui est démontrable est vrai

 Un système formel est complet ssi

si A alors A

 tout ce qui est vrai est démontrable


Calcul propositionnel
Intelligence Artificielle Programmation en Logique

Une autre règle d’inférence

 Principe de résolution (Robinson)


 Définitions
– littéral positif ou négatif: variable atomique (l ou l)
– une clause est une disjonction de littéraux (l1  l2  l3 … ln)
– la résolvante de C1 = l  C’1 et de C2 = l  C’2 est

C’1  C’2

 Principe de résolution

l  C’1 ,  l  C’2 réso C’1  C’2

– le principe de résolution est valide


– le principe de résolution généralise les autres règles
Calcul propositionnel
Intelligence Artificielle Programmation en Logique

Validité du principe de résolution

 Il faut montrer que :

l  C’1 ,  l  C’2 C’1  C’2

ie (l  C’1)  ( l  C’2 )  (C’1  C’2 )

 Il suffit de montrer que


si (l  C’1)  ( l  C’2 ) vrai alors (C’1  C’2 ) n’est pas faux

 Deux cas se présentent


 l est vrai
– nécessairement C’2 vrai et donc (C’1  C’2 ) aussi
  l est vrai
– nécessairement C’1 vrai et donc (C’1  C’2 ) aussi

 0 1  0 1  0 1
0 1 1 0 0 1 0 0 0
1 0 1 1 1 1 1 0 1
Calcul propositionnel
Intelligence Artificielle Programmation en Logique

Propriétés du calcul propositionnel

 Le calcul propositionnel muni du principe de


résolution est correct et complet

 Un ensemble S de clauses est insatisfaisable ssi


S reso (clause vide)

 Démonstration : par l’absurde (réfutation)

S C ssi S {C} reso 


On peut toujours se ramener à une forme
Rappel normale conjonctive (forme clausale)
Intelligence Artificielle Programmation Logique
Exemple
Soit:
F=(P  Q   R)  R   P  (T   Q)  T

 F= (P  Q   R)   R  P  (T   Q)  T

 F= ( P   Q  R)   R  P ( T  Q)  T

Soit SF ={P  Q  R, R, P, T  Q, T}


C1 C2 C3 C4 C5
SF est l'ensemble des clauses d'une fbf F.

Montrons que cet ensemble est insatisfiable

C1 = P  Q  R donc ( par résolution) C6 = P  Q


C2 = R

C6 = P  Q donc C7 = Q
C3 = P

C7 = Q donc C8 = T
C4 = T  Q

C8 = T donc C9 = Ø
C5 = T

A partir de l'ensemble des clauses de la fbf F on a déduit la clause vide donc


on peut conclure que F est insatisfiable et donc que F est valide.
Calcul propositionnel
Intelligence Artificielle Programmation en Logique

Ce qu’il faut retenir

 Intérêt d’une forme normale

 Conséquence logique vs démonstration

 Principe de résolution

 Preuve par réfutation


Intelligence Artificielle Connaissances/Logique

UTILISATION
Exemple:

1. "Si Ali n’écrit pas à Fatima, elle ne lui écrit pas non plus"
Par la réfutation:
2. " Fatima écrit à Ali" S={P  Q, Q}
alors « Ali écrit à Fatima" est vrai (conclusion)
On veut : S P
prémisses:
On montre alors que S U {P} est
1. "Si Ali n’écrit pas à Fatima, elle ne lui écrit pas non plus" inconsistant. Il faut dériver la
2. "Fatima écrit à Ali" clause vide par la Résolution.

conclusion: Les clauses:

alors " Ali écrit à Fatima" est vrai 1. P  Q


• correspondance en logique propositionnelle:
2. Q
soit P ≡ " Ali écrit à Fatima" et soit Q ≡ " Fatima écrit à Ali "

Prémisses: Nous avons donc les caluses:


3.  P
1.  P   Q
P  Q et Q
2. Q 4. P ( 1et2)
Avec la Règle de Résolution
Conclusion 5. Vide (3 et 4)
P. Nous aurons P
Intelligence Artificielle Programmation en Logique

2. Calcul des prédicats

 Comment écrire les formules ?


 Aspects syntaxiques

 Comment déterminer la valeur de vérité d’une


formule ?
 Aspects sémantiques

 Comment démontrer de nouveaux résultats ?


 Aspects déductifs
Calcul des prédicats
Intelligence Artificielle Programmation en Logique

Limites du calcul propositionnel

 Modéliser

 Les chandelles sont faites pour éclairer


 Quelques chandelles éclairent très mal
 Quelques objets qui sont faits pour éclairer le font très
mal
Calcul des prédicats
Intelligence Artificielle Programmation en Logique

Une modélisation

 Les chandelles sont faites pour éclairer


x, chandelle( x )  éclaire ( x )

 Quelques chandelles éclairent très mal


x, chandelle( x )  éclaireMal ( x )
 Quelques objets qui sont faits pour éclairer le font très
mal
x, éclaire ( x )  éclaireMal ( x )
Calcul des prédicats
Intelligence Artificielle Programmation en Logique

Syntaxe

 des connecteurs (, , ,  et )

 des quantificateurs ( et )

 des variables (x,y, …)

 des relations (prédicats) (R, S, éclaire, …)


 les relations d’arité 0 sont appelées des propositions

 des symboles de fonctions (f, g, …)


 les fonctions d’arité 0 sont appelées des constantes
Calcul des prédicats
Intelligence Artificielle Programmation en Logique

Vocabulaire

 Les termes
 les variables et les constantes sont des termes
 f(t1, …, tn) est un terme si
– les ti sont des termes
– f est un symbole de fonction d’arité n

 Les atomes
 R(t1, …, tn) est un atome si
– les ti sont des termes
– R est un symbole de relation d’arité n
Calcul des prédicats
Intelligence Artificielle Programmation en Logique

Formules

 Un atome est une formule


 Si F et G sont des formules et x une variable,
alors les expressions suivantes sont des formules

 (F)
 (F)  (G) et (F)  (G)
 (F)  (G) et (F)  (G)
 x (F) et x (G)
Calcul des prédicats
Intelligence Artificielle Programmation en Logique

Occurrence d’une variable

 Une occurrence d’une variable x dans une


formule F est un endroit où x apparaît dans F
sans être immédiatement précédée par  ou 

 Une occurrence libre de x dans F est définie :


Calcul des prédicats
Intelligence Artificielle Programmation en Logique

Occurrence libre

 Si F est un atome, toutes les occurrences de x sont libres

 Si F =  (G), les occurrences libres de x sont celles de G

 Si F = (G)  (H), les occurrences libres de x sont celles de


G et celles de H

 Si F = y(G) ou F = y(H) avec x distinct de y, les


occurrences libres de x sont celles de G et celles de H

 Si F = x(G) ou F = x(H), aucune occurrence de x dans


F n ’est libre
Calcul des prédicats
Intelligence Artificielle Programmation en Logique

Caractéristiques des variables

 Une variable est dite libre dans une formule F si


elle a au moins une occurrence libre (sinon on
dit qu’elle est liée)

 Une formule n’ayant pas de variable libre est


dite close
Calcul des prédicats
Intelligence Artificielle Programmation en Logique

Aspects sémantiques

 Formules universellement valides


 Le théorème de Herbrand
 Principe de résolution adapté au calcul des prédicats
Calcul des prédicats
Intelligence Artificielle Programmation en Logique

Vers la notion de modèle

 Soit L le langage du calcul des prédicats


 une interprétation de L c’est la donnée de :
– un ensemble E non vide appelé ensemble de base
– pour chaque symbole de prédicat R d’arité n, d’un sous-
ensemble R’ de En
– pour chaque symbole de fonction f d’arité n, d’une
application f’ de En vers E (y compris pour les constantes)
 on peut alors calculer la valeur de tout terme clos
(c’est un élément de E)
 on peut donc associer une valeur de vérité à tout
atome et donc par extension à toute formule close
Calcul des prédicats
Intelligence Artificielle Programmation en Logique

Exemple d’interprétation

 xyz (P(x,y)  Q(y,z)  R(x,z))


 xy ( (M(x,y)  P(x,y)  Q(x,y))
 M(a,b)  P(c,b)  P(d,a)  P(e,c)

 E = { aicha, hamid, …}
M’ = est la mère de
 P’ = est le père de Q’ = est un parent de
R’ = est le grand-père de

 a’ = aicha b’ = hamid c’ = ahmed


d’ = ali e’= moha,..
Calcul des prédicats
Intelligence Artificielle Programmation en Logique

Modèle

 Soit M une interprétation de L


 soit F une formule close. M est un modèle de F ssi la
valeur de vérité de F dans M est 1
M F
 soit F(x1, …, xk) une formule quelconque
– F est dite universellement valide ssi
x1…xk F(x1, …, xk)
est satisfaite dans toutes les interprétations de L

– F est dite insatisfaisable ssi il existe une interprétation


pour laquelle
x1…xk F(x1, …, xk)
est satisfaite
Calcul des prédicats
Intelligence Artificielle Programmation en Logique

Preuve et démonstration

 Comment prouver une formule du calcul des


prédicats ?

 Prouver qu’elle est vraie


– passer en revue toutes les interprétations !

 Prouver qu’elle est fausse


– trouver une interprétation qui invalide la formule
Calcul des prédicats
Intelligence Artificielle Programmation en Logique

Toutes les interprétations ?

 Une représentation utile des formules


 forme clausale

 Un théorème qui simplifie la vie


 théorème de Herbrand

 Principe de résolution pour le calcul des prédicats


 vers une automatisation des démonstrations
Calcul des prédicats
Intelligence Artificielle Programmation en Logique

Transformation de formule

 Forme normale prénexe


 quantificateurs en tête de la formule
 formule sous forme normale conjonctive

 Forme standard de Skolem


 formule sous forme normale prénexe
 quantificateurs existentiels précédant quantificateurs
universels

Tout formule du calcul des prédicats est équivalente à


une formule sous forme standard de Skolem
Calcul des prédicats
Intelligence Artificielle Programmation en Logique

Mise sous forme prénexe

 Éliminer les connecteurs  et 

 Transporter les  devant les atomes


 en utilisant ( F  F) et les lois de De Morgan

 Transporter les quantificateurs en tête de la


formule

 Ne pas hésiter à renommer les variables


Calcul des prédicats
Intelligence Artificielle Programmation en Logique

Transport des quantificateurs

x F   x F  x y F   y  x F
x F   x F xy F  yx F

x F  x H  x F  H 
x F  x H  x F  H 
si H ne contient aucune occurrence de x

x F   H  x F  H  x H  H
x F   H  x F  H  x H  H
Calcul des prédicats
Intelligence Artificielle Programmation en Logique

Inversion de  et de 
Skolemisation

 Lorsqu’on a

 x y f ( x )  y
 on remplace y par une fonction g qui à x associe y

g x f ( x )  g ( x )

Skolemisation = expliciter l’implicite


Calcul des prédicats
Intelligence Artificielle Programmation en Logique

Une représentation utile des formules


Forme clausale

 On part de la forme standard de Skolem

 On utilise les clauses avec :


 les variables quantifiées universellement conservées
 les fonctions de Skolem conservées
 les variables quantifiées existentiellement remplacées
par des constantes
 les variables renommées d’une clause à l’autre

x y z p( x, y )  q( z, y, x ) 
p(a, y1 ) ; q( z1 , y2 , a )
Exemple

Forme prenexe

Soit la formule  x (p(x) ->  x p(x))


Éliminer -> :  x (~p(x) v  x p(x))
Renommer  x p(x) en  y p(y) :  x (~p(x) v  y p(y))
Sortir  y :  x  y (~p(x) v p(y))
N.B. : le renommage est essentiel ici ;
par ex.  x (~p(x) v  x p(x)) n'est pas équivalent à  x  x (~p(x) v p(x) )

Forme normale de Skolem

x  y (~p(x) v p(y))
On pose : y= f(x)
x (~p(x) v p(y))

Et
~p(x) v p(f(x))
Calcul des prédicats
Intelligence Artificielle Programmation en Logique

Univers de Herbrand

 Soit S un ensemble de clauses


 Soit H0 l’ensemble des symboles de constantes ayant
au moins une occurrence dans S. On pose :
H i  H i 1  f n (t1 ,..
 , tn )
pour fn fonction d’arité n de S et tj éléments de Hi-1

 H= limi Hi est appelé univers de Herbrand

 On appelle instance de base d’une clause C toute


clause obtenue en remplaçant les variables de C par
des éléments de H
 
    
    
    
    

    
    
    
                                           

                                                         
                                                         
                                  
Calcul des prédicats
Intelligence Artificielle Programmation en Logique

Théorème de Herbrand

 Théorème Un ensemble S de clauses est


insatisfaisable si et seulement si il existe un
ensemble S’ d’instances de base insatisfaisable

 Corollaire Un ensemble de clauses est


satisfaisable si et seulement si tout ensemble
fini d’instances de base est satisfaisable
Calcul des prédicats
Intelligence Artificielle Programmation en Logique

A quoi ça sert ?
Validation de raisonnement

 On cherche à valider le raisonnement suivant

 Un dragon est heureux si tous ses enfants peuvent voler (P1)


 Les dragons verts peuvent voler (P2)
 Un dragon est vert s’il a au moins un parent vert ou rose (P3)
 Donc les dragons verts sont heureux (C)
Calcul des prédicats
Intelligence Artificielle Programmation en Logique

Résolution du problème
 Démarche générale
 Modéliser le problème (les prémisses et la conclusion)
 Démonstration par l’absurde, on montre que
P1  P2  P3  C est insatisfaisable
– mettre la formule sous forme clausale
– utiliser le théorème de Herbrand

 Notations
 h(x) : x est heureux
 p(x,y) : x est parent de y
 vo(x) : x vole (peut voler)
 ve(x) : x est vert
 r(x) : x est rose
Calcul des prédicats
Intelligence Artificielle Programmation en Logique

Résolution du problème (suite)

P1 un dragon est heureux si tous ses enfants peuvent voler


x (y, p(x,y)vo(y)) h(x) x , xx,y p,y(,ypxp,(,
,,y (pxyxp,(),xy(y,x))y,h
y)(
)x vo
)vo
 vo )y)vo
((y(y )
(hhy(h(x)(x)x))h( x ) 
f , x,  p( x, f ( x ))  h( x )   vo( f ( x ))  h( x ) 
P2 les dragons verts peuvent voler
x, ve( x )  vo( x ) x, ve( x )  vo( x )

P3 un dragon est vert s’il a au moins un parent vert ou rose


x, y , p( y , x )  ve( y )  r ( y )   ve( x )
les x , xA x,xp,(A
, y,
,y  ysont
 (xyy),
p, ,yxB,)(pve
p y(, x,ve
y(B y)x))(y)ve

ve ( x()
y)(
p y )rve
r,(prxy())y,)x ()x(r)x(
(ve
y )y )ve x)( x) 
(ve
C les dragons verts sont heureux
x, ve( x )  h( x ) xx,,x,  ve(ve(xx())x
ve hh((xx))
)
négation
Calcul des prédicats
Intelligence Artificielle Programmation en Logique

Forme clausale

f , x,  p( x, f ( x ))  h( x )   vo( f ( x ))  h( x ) 
x, ve( x )  vo( x )
x, y, p( y, x)  ve( y)  ve( x)  p( y, x)  r ( y)  ve( x)
x, ve( x )  h( x )

p( x1 , f ( x1 ))  h( x1 ) vo( f ( x2 ))  h( x2 )
ve( x3 )  vo( x3 ) p( y1 , x4 )  ve( y1 )  ve( x4 )
p( y2 , x5 )  r ( y2 )  ve( x5 ) ve(a ) h (a )
Calcul des prédicats
Intelligence Artificielle Programmation en Logique

Validation du raisonnement

 Univers de Herbrand
 H0 = {a} H1= {a, f(a)} H = {a, …, fn(a)}

 Trouver un ensemble d’instances de base insatisfaisable


 intuition 1 : partir de la conclusion et essayer d’arriver
à une contradiction par déduction
 intuition 2 : utiliser le principe de résolution
Calcul des prédicats
Intelligence Artificielle Programmation en Logique

Mise en œuvre

p( x1 , f ( x1 ))  h( x1 ) vo( f ( x2 ))  h( x2 )
ve( x3 )  vo( x3 ) p( y1 , x4 )  ve( y1 )  ve( x4 )
p( y2 , x5 )  r ( y2 )  ve( x5 ) ve(a ) h (a )

h (a ) h( a )  vo( f ( a )) vo( f (a ))  ve( f (a ))


x2  a x3  f ( a )
x4  f ( a )
 clause vide
p( y1 , f (xa ))
a
 ve(xy1) f(ave
 ( f ( a ))
) h (a )
2 3
x1  a y1  x1
h(a )  p( a, f (a )) vo(pf((aa, ))f (a vo
))ve
 (( af())
(fve a( a) ))
 veh((fa()a ))
h (a ) ve(a )
Calcul des prédicats
Intelligence Artificielle Programmation en Logique

Résolution

 On a un ensemble d’instances de base insatisfaisable

h (a ) h (a ) vo( f ( a ))  ve( f (a ))
h (a )  vo( f ( a ))

p( a, f ( a ))  ve( a )  ve( f (a )) h(a )  p( a, f (a ))

ve(a )

 La formule P1  P2  P3  C est donc insatisfaisable


 Le raisonnement est donc valide
Calcul des prédicats
Intelligence Artificielle Programmation en Logique

Analysons un peu les choses

 L’opération d’appariement de deux atomes


s’appelle l’unification

p( y1 , f ( a ))  ve( y1 )  ve( f ( a ))


p( x1 , f ( x1 ))  h( x1 )
unificateur y1  x1 x1  a

 Algorithme d’unification (vu plus tard)


 On peut donc appliquer le principe de
résolution sans problème
Calcul des prédicats
Intelligence Artificielle Programmation en Logique

Propriétés du calcul des prédicats

 Le calcul des prédicats muni du principe de


résolution et de l’unification est complet
 toute formule close est vraie ou fausse

 MAIS le calcul des prédicats est semi-décidable


 Il n’existe pas d’algorithme permettant de décider à tout
coup si une formule close est fausse ( la procédure peut
ne pas s’arrêter)

 En PROLOG, nous nous limiterons donc à un sous-


ensemble du calcul des prédicats
 non restrictif en pratique
Calcul des prédicats
Intelligence Artificielle Programmation en Logique

Programmer en logique ?

 Un petit exemple
 xyz (pere(x,y)parent(y,z)  grand-pere(x,z)
 xy ((mere(x,y)  pere(x,y))  parent(x,y)
 mere(a,b) pere(c,b) pere(d,a) pere(e,c)
 Forme clausale
 pere(x1, y1)  parent(y1, z1)  grand-pere(x1,z1)
 mere(x2, y2)  parent(x2, y2)
 pere(x3, y3)  parent(x3, y3)
 mere(a,b) pere(c,b) pere(d,a) pere(e,c)
 On veut prouver x, grand-pere(x,b)
 négation sous forme clausale : grand-pere(x,b)
Calcul des prédicats
Intelligence Artificielle Programmation en Logique

Programmer en logique ?
pere(x1, y1)  parent(y1, z1)  grand-pere(x1,z1)
mere(x2, y2)  parent(x2, y2)
pere(x3, y3)  parent(x3, y3)
mere(a,b) pere(c,b) pere(d,a) pere(e,c)

 On part de grand-pere(x,b)
 si x = x1 et z1=b unification avec
pere(x1, y1)  parent(y1, z1)  grand-
pere(x1,z1)
 on obtient pere(x, y1)  parent(y1, b)
 si y3 = b et y1=x3 unification avec
pere(x3, y3)  parent(x3, y3)
 on obtient pere(x, x3)  pere(x3, b)
 si x3 = c unification avec pere(c,b)
 on obtient pere(x, c)
 si x=e unification avec pere(e,c)
 on obtient  QED
Calcul des prédicats
Intelligence Artificielle Programmation en Logique

Programmer en logique ?

 On a réussi à prouver x, grand-pere(x,b)

 On a réussi à calculer un x

 Unification = calcul
 on donne des valeurs aux variables

 Calcul = programmation
 on va pouvoir programmer avec la logique !!!
 on automatise complètement le processus
 PROLOG est un démonstrateur de théorème
Intelligence Artificielle Programmation en Logique

Le langage PROLOG

1. Premiers pas
2. Arithmétique
3. Listes
4. Le contrôle PROLOG
5. Termes structurés
6. Méta-interprétation de PROLOG
Le langage
Intelligence Artificielle Programmation en Logique

1. Premiers pas en Prolog

 On se limite aux clauses de Horn


 au plus un littéral positif
– un seul littéral (positif) : fait
– un littéral positif et au moins un littéral négatif : règle
– pas de littéral positif : requête

 Elles permettent
 de forcer le retour dans la base pour continuer la
démonstration
 de limiter le choix par clause
Le langage
Intelligence Artificielle Programmation en Logique

Univers PROLOG

 L’univers PROLOG est une base de connaissances


décrivant l’état du monde à l’aide de relations (prédicats)
portant sur des entités (termes)

 Un prédicat particulier (=) correspond à l’unification


Le langage
Intelligence Artificielle Programmation en Logique

Syntaxe de PROLOG

 Considérons l’énoncé
 Socrate est un homme
 Tout homme est mortel
 Socrate est-il mortel ?

Calcul des prédicats Prolog


x, homme(x) homme(socrate).

x, homme(x)  mortel(x) mortel(X) :- homme(X).

?- mortel(socrate).
Le langage
Intelligence Artificielle Programmation en Logique

La famille
masculin(tom). % tom est de sexe masculin
masculin(tim).
masculin(bob).
masculin(jim). % «paquet» de clauses

feminin(pam).
feminin(liz).
feminin(ann).
feminin(pat).

enfant(bob,pam).
enfant(bob,tom).
enfant(liz,tom).
enfant(ann,bob).
enfant(pat,bob).
enfant(tim,liz).
enfant(jim,pat).
Intelligence Artificielle Programmation en Logique Le langage

Premières requêtes masculin(tom).


masculin(tim).
masculin(bob).
masculin(jim).

feminin(pam).
feminin(liz).
feminin(ann).
feminin(pat).

enfant(bob,pam).

Est-ce que pat est un enfant de bob ? enfant(bob,tom).


enfant(liz,tom).
enfant(ann,bob).
enfant(pat,bob).
enfant(tim,liz).
?- enfant(pat,bob). enfant(jim,pat).

Yes

Quels sont les enfants de tom ?

?- enfant(X,tom).
X = bob ;
X = liz ;
No
Intelligence Artificielle Programmation en Logique

Lien avec le calcul des prédicats

Règles PROLOG Règles LOGIQUE


a :- b,c,d. abcd

Requête PROLOG Requête LOGIQUE


?- q. q

Unification
Faire correspondre requête et tête de règle
Intelligence Artificielle Programmation en Logique Le langage

Écriture de prédicats masculin(tom).


masculin(tim).
masculin(bob).
masculin(jim).

feminin(pam).
feminin(liz).
feminin(ann).
feminin(pat).

X=pam enfant(bob,pam).

• Qui est le père de bob ? X=tom enfant(bob,tom).


enfant(liz,tom).
enfant(ann,bob).
enfant(pat,bob).
enfant(tim,liz).
?- enfant(bob,X), masculin(X). enfant(jim,pat).

retour échec

X=tom

• Plus généralement
pere(X,Y) :-
enfant(Y,X),
masculin(X).
• Écrire le prédicat mere/2
Le langage
Intelligence Artificielle Programmation en Logique

À chacun son tour

 Écrire les prédicats correspondant aux relations


 grand-pere/2
 frere/2
 tante/2
 cousin/2
Le langage
Intelligence Artificielle Programmation en Logique

PROLOG

 PROLOG est un langage déclaratif

on spécifie les propriétés du résultat du programme et


non pas le processus pour arriver à ce résultat (aspect
opérationnel)

 Intérêts
 facilité de compréhension
 facilité d’écriture
Le langage
Intelligence Artificielle Programmation en Logique

Retour sur le retour arrière masculin(tom).


masculin(tim).
masculin(bob).
masculin(jim).

feminin(pam).
feminin(liz).
feminin(ann).
feminin(pat).

retour
 Considérons la requête Z=pam enfant(bob,pam).
Z = tom enfant(bob,tom).
enfant(liz,tom).
enfant(ann,bob).
 ?- frere(bob,liz). échec enfant(pat,bob).
enfant(tim,liz).
enfant(jim,pat).

Yes X = bob, Y = liz frere(X,Y) :-


masculin(X),
enfant(X,Z),
enfant(Y,Z).

Le mécanisme de retour-arrière (backtrack) assure


la complétude de la recherche

Demander une nouvelle solution revient à provoquer


un échec fictif pour forcer le backtrack
Le langage
Intelligence Artificielle Programmation en Logique

Quelques propriétés

 la recherche réalisée par PROLOG est une


recherche en profondeur d’abord
 on peut obtenir plusieurs solutions pour une
même requête
 on appelle cela le non-déterminisme de PROLOG
 un prédicat peut servir à autre chose que ce
pour quoi il a été écrit
 on appelle cela la réversibilité de PROLOG
 les seuls résultats possibles : yes ou no
 pas de fonction, les réponses sont obtenues par
unification uniquement
Le langage
Intelligence Artificielle Programmation en Logique

Récursivité

 Écrire le prédicat ascendant/2

ascendant(X,Y) :- Condition d’arrêt


en premier
enfant(Y,X).

ascendant(X,Z) :-
Information discriminante
enfant(Z,Y), en premier
ascendant(X,Y).
Le langage
Intelligence Artificielle Programmation en Logique

PROLOG = logique ?

 Soit une relation binaire r. Comparer :


 récursion droite
fermeture(X,Y) :- r(X,Y).
fermeture(X,Z) :- r(X,Y), fermeture(Y,Z).
 récursion gauche
fermeture(X,Y) :- r(X,Y).
fermeture(X,Z) :- fermeture(Y,Z), r(X,Y).
 Attention à la procédure de recherche !!!
 Règle de sélection du but
– le plus à gauche
 Règle de sélection de la clause
– la première
Le langage
Intelligence Artificielle Programmation en Logique

2. Arithmétique
 Les opérateurs usuels existent : +, , /, mod
 attention il s’agit de symboles de fonctions !!!
?- X = 1 + 2.
X= 1+2  +(1,2)

• Un opérateur spécial is
?- X is 1 + 2.
X=3
• L’argument de droite doit être complètement
instancié à l’appel
?- X is 1 + Y.
{INSTANTIATION ERROR}
Le langage
Intelligence Artificielle Programmation en Logique

Opérateurs arithmétiques

 > et <
 >= et =<
 =:= égalité numérique
 =\= inégalité numérique

attention : les deux arguments


doivent être instanciés à l’appel
Le langage
Intelligence Artificielle Programmation en Logique

Exemple: calcul du PGCD

 Propriétés du PGCD D de X et Y
 si X et Y sont égaux, D vaut X
 si X < Y alors D est le PGCD de X et de Y - X
 si Y < X alors échanger le rôle de X et Y

pgcd(X, X
Y,X X=Y
D)).:- X =:= Y , D is X.
pgcd(X, Y , D) :-
X<Y,
pgcd(X,Y-X,D).
Y1 is Y - X,
pgcd(X,Y1,D).

pgcd(X, Y, D) :-
X > Y,
pgcd(Y,X,D).
Le langage
Intelligence Artificielle Programmation en Logique

Attention …

 X = Y réussit si X s’unifie avec Y sinon échec


 X is Y réussit si Y est une expression arithmétique
complètement instanciée à l’appel et X est une variable
libre sinon il y a erreur
 X =:= Y réussit si X et Y sont deux expressions
arithmétiques de même valeur sinon, il y a échec ou
erreur selon le cas
 X == Y réussit si les termes sont identiques (pas
simplement unifiables)
 X \== Y réussit si les termes ne sont pas identiques
Le langage
Intelligence Artificielle Programmation en Logique

3. Listes

 La liste vide : []
 Les listes non vides :
 [a, b, c]
 [a, [b, c], d]
 Le constructeur de listes : |
 [Tete | Reste]
 [a]  [a | [] ]
 [a, b]  [a | [b |[]]]  [a | [b] ]
 Analogie avec Haskell
 |=:
 représentation arborescente
Le langage
Intelligence Artificielle Programmation en Logique

Prédicats de base

 Appartenance à une liste : member/2

member(X, [X|Ys]).
_ Ys ne sert à rien
member(X, [Y_ |Xs]) :- Y ne sert à rien
member(X,Xs).

 Longueur d’une liste : length/2

length([], 0).
length([_ | Xs], N1) :-
length(Xs, N),
N1 is N + 1.
Le langage
Intelligence Artificielle Programmation en Logique

Prédicats de base (suite)

 Suppression d’un élément d’une liste : efface/3


efface(_, [], []).
efface(X,[X|Ys], Ys).
efface(X,[Y|Ys], [Y|Zs]) :-
X \== Y,
efface(X,Ys,Zs)

Comment effacer toutes les occurrences d’un élément ?


Le langage
Intelligence Artificielle Programmation en Logique

Prédicats de base (suite)

 Concaténation de deux listes: append/3

append([], Ys, Ys).


append([X|Xs], Ys, [X|Zs]) :-
append(Xs,Ys,Zs).

 Une nouvelle version de member ?

member(X,L) :-
append(_, [X|_], L).
Le langage
Intelligence Artificielle Programmation en Logique

Prédicats de base (suite)

 Renversement d’une liste : reverse/2


reverse([], []).
reverse([X|Xs], Ys) :-
reverse(Xs,Zs),
append(Zs, [X], Ys).
 Une autre version de reverse ?
nreverse([], L, L).
nreverse([X|Xs], Ys, L) :-
nreverse(Xs, [X|Ys], L).
nreverse(Xs, Ys) :-
nreverse(Xs, [], Ys).
Le langage
Intelligence Artificielle Programmation en Logique

Un prédicat plus délicat

 Permutation d’une liste : permute/2

insere(X,Ys,[X|Ys]).
insere(X,[Y|Ys], [Y|Zs]) :-
insere(X,Ys,Zs).

permute([], []).
permute([X|Xs], Ys) :-
permute(Xs,Zs),
insere(X,Zs,Ys).
Le langage
Intelligence Artificielle Programmation en Logique

4. Le contrôle PROLOG

 Contrôle du backtrack
 Soit une fonction f dont une définition Prolog peut être :

f(X, 0) :- X < 3.
f(X, 2) :- 3 =< X, X < 6.
f(X, 4) :- 6 =< X.

 Que se passe-t-il si on pose la question ?


?- f(1,Y), 2 < Y.
Le langage
Intelligence Artificielle Programmation en Logique

?- f(1,Y), 2 < Y. f(X, 0) :- X < 3.


f(X, 2) :- 3 =< X, X < 6.
f(X, 4) :- 6 =< X.

Démonstration de f(1,Y)

Première règle : Y = 0
Démonstration de 2 < Y :- échec

Deuxième règle : échec

Troisième règle : échec


Le langage
Intelligence Artificielle Programmation en Logique

La coupure : !

 On appelle but père le but ayant permis


d’unifier la clause contenant la coupure (! cut)
 L’effet du cut est de couper tous les points de
choix restant depuis le but père. Les autres
alternatives restent en place

f(X, 0) :- X < 3, !.
f(X, 2) :- 3 =< X, X < 6, !.
f(X, 4) :- 6 =< X.

 ?- f(7,Y).
Le langage
Intelligence Artificielle Programmation en Logique

Si … alors … sinon

 Le cut peut servir à exprimer des conditions


mutuellement exclusives et ainsi simplifier
l’écriture
 La clause suivant un cut peut être considérée
comme un sinon

f(X, 0) :- X < 3, !.
f(X, 2) :- X < 6, !.
f(X, 4).

 ?- f(1,2).
Le langage
Intelligence Artificielle Programmation en Logique

Un usage délicat

 Green cut : la sémantique déclarative du


programme n’est pas modifiée
 on peut enlever le cut le programme fonctionnera
toujours

 Red cut : la sémantique déclarative du


programme est modifiée
 Le retrait du cut conduit à un programme au
fonctionnement erroné
 Généralement, la version avec cut peut être prise en
défaut
Le langage
Intelligence Artificielle Programmation en Logique

Autres prédicats de contrôle

 true est un but qui réussit toujours


 p(a,b).  p(a,b) :- true.

 fail est un but qui échoue toujours

 call(X) est un méta but. Il considère X comme


un but et essaie de le résoudre.
 ?- Y=b, X=member(Y, [a,b,c]), call(X).
Yes
 Note: call(X)  X dans Sicstus Prolog.
Le langage
Intelligence Artificielle Programmation en Logique

Application : négation

 Expression de la négation en Prolog


 different(X, Y) :-
X = Y, !, fail.
different(X, Y).

 Un prédicat plus général :


 not(P) :-
P, !, fail.
not(_).
Le langage
Intelligence Artificielle Programmation en Logique

Problèmes avec le not !

r(a).
q(b).
p(X) :- not( r(X) ).

 ?- q(X), p(X).

 ?- p(X), q(X).
Le langage
Intelligence Artificielle Programmation en Logique

Théorie du monde clos

 not(X)
 ne veut pas dire
– X est toujours faux
 veut simplement dire
– Je n’ai pas assez d’information pour prouver X

 Prolog considère ce qui n’est pas vrai comme


faux et vice-versa
 c’est la théorie du monde clos

 A quoi peut servir : not(not(P)) ?


Le langage
Intelligence Artificielle Programmation en Logique

Typage en Prolog

 var/1, nonvar/1

 integer/1, float/1, number/1

 atom/1, string/1, atomic/1

 compound/1

 ground/1
Le langage
Intelligence Artificielle Programmation en Logique

5. Termes structurés

 Notion de foncteur
famille(
indiv(tom, fox, date(7, mai, 1950), travail(emn, 7850)),
indiv(ann, fox, date(9, mai, 1951), sans-emploi),
[ indiv(pat, fox, date(5, mai, 1973), sans-emploi),
indiv(jim, fox, date(5, mai, 1973), sans-emploi) ])

On pourrait utiliser des listes (de listes …)


mais on préfère structurer l’information
Le langage
Intelligence Artificielle Programmation en Logique

Utilisation de l’unification
famille(
indiv(tom, fox, date(7, mai, 1950), travail(emn, 7850)),
indiv(ann, fox, date(9, mai, 1951), sans-emploi),
[ indiv(pat, fox, date(5, mai, 1973), sans-emploi),
indiv(jim, fox, date(5, mai, 1973), sans-emploi) ])

 Les familles à trois enfants :

 famille(_,_,[_,_,_]).

 Les femmes mariées ayant au moins trois


enfants

 famille(_,indiv(Prenom, Nom,_,_), [_,_,_|_]).


Le langage
Intelligence Artificielle Programmation en Logique

Outils de manipulation

 Consultation de termes structurés


 functor/3
?- functor(date(9, janvier, 1973), F, A)
F = date, A = 3
 arg/3
?- arg(3, date(9, janvier, 1973), F)
F = 1973

 Construction/déconstruction de termes structurés


 =../2
?- X =.. [date, 9, janvier, 1973]
X = date(9, janvier, 1973)
Le langage
Intelligence Artificielle Programmation en Logique

Opérateurs

 On peut définir de nouveaux opérateurs. Il ne


s’agit que d’une définition syntaxique pour
faciliter l’écriture de termes.

:- op(80, fy, non).


:- op(100, yfx, et).

 non a et b est devenu un terme valide, il est


équivalent à et(non(a), b)
Le langage
Intelligence Artificielle Programmation en Logique

Fonctionnement
 Un opérateur possède une précédence (1..1200)
 par exemple : + a une plus forte précédence que / car

a+b/c se lit a+(b/c)

 Un opérateur possède une politique de résolution des


ambiguïtés :
 xfx correspond aux opérateurs infixes non associatifs
les deux sous-expressions ont un niveau de précédence inférieur à
celui de l’opérateur
 xfy correspond aux opérateurs associatifs à droite seule
l’expression de gauche doit avoir un niveau inférieur à l’opérateur
 yfx correspond aux opérateurs associatifs à gauche
Le langage
Intelligence Artificielle Programmation en Logique

6. Méta-interprétation

 Méta-programmation

 écrire des programmes qui analysent, transforment


et simulent d’autres programmes

 Prolog est un langage adapté à la méta-


programmation car :

 il y a identité entre programme et données


Le langage
Intelligence Artificielle Programmation en Logique

Méta-interprétation

 Un méta-interprète d’un langage donné est un


interprète du langage écrit dans le même
langage

 Le prédicat prouve(But) réussit si la requête


But par rapport au programme que l’on cherche
à interpréter

 Le plus simple des méta-interprètes Prolog

prouve(But) :- But.
Le langage
Intelligence Artificielle Programmation en Logique

Outils pour la méta-interprétation

 Le prédicat clause/2 (accès aux programmes)

append([],X,X).
append([X|Xs], Ys, [X|Zs]) :-
append(Xs,Ys,Zs).
?- clause(append(X,Y,Z), Corps).

X = [], Y = _A1, Z=_A2, Corps = true ? ;

X = [_A1|_A2], Y = _A3, Z = [_A1|_A4],


Corps = append(_A2, _A3, _A4) ?;

no
Le langage
Intelligence Artificielle Programmation en Logique

Un premier interprète

prouve( true ).

prouve( (A,B) ) :-
prouve(A),
prouve(B).

prouve( But ) :-
clause(But, Corps),
prouve(Corps).
Le langage
Intelligence Artificielle Programmation en Logique

Améliorations
 Gestion des prédicats prédéfinis

prouve( But ) :-
predefini( But ), predefini( _ = _ ).
But. predefini( _ is _ ).

 Gestion explicite de l’unification

prouve( But ) :-
But =.. [Foncteur|Arguments],
Tete =.. [Foncteur|AutresArguments],
clause(Tete, Corps),
unification(But, Tete),
prouve(Corps).
Le langage
Intelligence Artificielle Programmation en Logique

Algorithme d’unification

unification( X, Y) :-
var(X), !, Y = X. % nooccur(X,Y)

unification( X, Y) :-
var(Y), !, X = Y. % nooccur(Y,X)

unification( X, Y) :-
atomic(X), atomic(Y), X == Y.

unification( X, Y) :-
X =.. [Foncteur|Arguments],
Y =.. [Foncteur|AutresArguments],
unificationListe(Arguments, AutresArguments).

unificationListe([], []).
unificationListe([X|Xs], [Y|Ys]) :-
unification(X,Y),
unficationListe(Xs,Ys).
Le langage
Intelligence Artificielle Programmation en Logique

Le test d’occurrence

 Théoriquement, lors d’une unification il faut


réaliser le test d’occurrence. Prolog ne le fait
pas. En particulier :
?- X = f(X).

réussit mais ne peut afficher de résultat !

 Exercice : écrire le test d’occurrence en Prolog


Le langage
Intelligence Artificielle Programmation en Logique

nooccur/2

noccur( _, Y) :-
ground(Y).

noccur( X, Y) :-
var(Y), X \== Y.

noccur( X, Y) :-
Y =.. [_|Arguments],
nooccurListe(X, Arguments).

nooccurListe(_, []).
nooccurListe(X, [Y|Ys]) :-
nooccur(X,Y),
nooccurListe(X,Ys).
Intelligence Artificielle Programmation en Logique

PROLOG avancé

1. Structures incomplètes
2. Listes de solutions
3. Modifications de la base
4. Indexation de clauses
Prolog avancé
Intelligence Artificielle Programmation en Logique

1. Structures incomplètes

 Concaténation
append([], Ys, Ys).
append([X|Xs], Ys, [X|Zs]) :-
append(Xs,Ys,Zs).

 Notoirement inefficace !
 Le problème
– pas de « pointeur » sur le dernier élément
– pas de possibilité de modification d’une variable logique
 uniquement instanciation d’une inconnue
Prolog avancé
Intelligence Artificielle Programmation en Logique

Une solution : listes de différences

 Une nouvelle structure de liste


 idée : conserver une partie inconnue pour
instanciation au dernier moment
 Liste de différence
– on nomme la fin de la liste
– [a,b,c] est représentée par [a,b,c|Xs]-Xs
– la liste vide Xs-Xs
 Concaténation en une opération
append(Ls-Xs, Xs-Rs, Ls-Rs).

?- append([a,b,c|Xs]-Xs, [1,2,3|Ys]-Ys, R).


R = [a,b,c,1,2,3|Ys]-Ys
Prolog avancé
Intelligence Artificielle Programmation en Logique

Une opération !?!

Ls - Xs abc 123??? - 123???


Xs - Rs 123??? - ???

Ls - Rs abc123??? - ???

Merci l’unification !
Prolog avancé
Intelligence Artificielle Programmation en Logique

2. Listes de solutions
pere(tarzan, fils).
pere(tarzan, fille).

age(fils, 5).
age(fille, 2).
age(tarzan, 25).

 On veut la liste de tous les enfants de tarzan et leur


âge.
 pere(tarzan, X), age(X,A) ne donne les solutions
qu’une par une
 Comment les récupérer toutes dans une liste ?
Prolog avancé
Intelligence Artificielle Programmation en Logique

Prédicats « toutes solutions »

?- setof(X/A, (pere(tarzan, X), age(X,A)), L).


L = [fils/5, fille/2]

 setof/3 résultat trié (fail si pas de solution)


 bagof/3 résultat tel que le backtrack (fail si pas de
solution)
 findall/3 résultat tel que le backtrack ([] si pas de
solution)

findall(X, member(X/Y, [b/1, a/2]), L) --> [b,a]


setof(X, member(X/Y, [a/1, b/2]), L --> L=[b] Y=1 ;
L=[a] Y=2
setof(X, Y^member(X/Y, [b/1, a/2]), L) --> [a,b]
Prolog avancé
Intelligence Artificielle Programmation en Logique

3. Modifications de la base

 Besoin : résistance au backtrack

 Ajout dans la base


 assert/1
 asserta/1
 assertz/1
 Retrait dans la base
 retract/1
 retractall/1
Prolog avancé
Intelligence Artificielle Programmation en Logique

4. Indexation de clause

 Les clauses Prolog sont rangées dans une


hashtable. Elles sont indexées par le foncteur
et l’arité de leur premier argument

 Pour écrire des programmes plus efficaces,


mettre en tête l’argument le plus discriminant.

Vous aimerez peut-être aussi