1. Rappels sur les Systèmes à Base de Connaissances

1.1. Complexité des algorithmes et des problèmes

Soit à écrire un programme qui calcule la somme des n premiers nombres entiers. Un informaticien écrira :
lire n
s <- 0
pour i variant de 1 à n
  s <- s + i
finpour
imprimer s
La complexité de cet algorithme est O(n).
Un mathématicien écrira :
lire n
imprimer (n * (n + 1) / 2)
La complexité de cet algorithme est O(1).
On ne peut pas faire mieux. C'est donc la complexité de ce problème.
Soit maintenant à écrire un algorithme qui trie un tableau de nombres. Un débutant écrira une boucle de 1 à n-1, au sein de laquelle il comparera deux cases successives, en les permutant si elles ne sont pas dans l'ordre. Et il plongera cette boucle dans une autre de 1 à n. La complexité de son algorithme sera O(n2).
On montre qu'en fait, la complexité du problème est O(n log(n)).
Soit maintenant à écrire un programme qui joue un coup aux échecs. On développe l'arbre de tous les coups possibles (alternativement coup ami et coup ennemi), jusqu'à une profondeur n, puis on calcule une fonction d'évaluation sur chaque feuille, et on remonte alternativement le max et le min des notes obtenues.
La complexité de cet algorithme est O(pn), où p est le nombre moyen de coups légaux dans un état donné.
Pour revenir un peu sur terre, comparons n2 et 2n, pour n=100, en supposant une micro-seconde par opération :

C'est-à-dire à peu près un million de fois l'age de l'univers ! Inutile de chercher à acheter une machine mille fois ou un million de fois plus rapide ; il faut abandonner l'espoir de résoudre le problème.

1.2. Notion d'heuristique

Et pourtant... Je connais, et vous connaissez aussi, des gens qui résolvent un tel problème en quelques minutes, alors que leur "hardware" est environ 107 fois moins rapide que celui d'un ordinateur. Donc, ils n'utilisent pas l'algorithme que nous avons évoqué au paragraphe précédent. Qu'utilisent-ils? Ce que nous appellerons des heuristiques, ou plus généralement des connaissances. Mettons les en évidence sur un petit problème. Soit à résoudre le problème de cryptarithmétique :
  S E N D
  M O R E
---------
M O N E Y
Il s'agit de trouver une bijection entre les lettres et des chiffres (S et M ne pouvant être nuls) pour que l'addition soit correcte en base 10. Le seul algorithme que je connaisse consiste à faire 8 boucles imbriquées de 0 à 9 pour essayer toutes les valeurs possibles pour chacune des lettres : il est typiquement exponentiel. Mais, grace à mes connaissances, je vais résoudre ce problème en temps linéaire :
J'ai donc résolu en temps quasi-linéaire un problème pour lequel le seul algorithme connu est exponentiel. Miracle? Non :
algorithme heuristiques
temps de calcul 10n n + epsilonn
taille du programme 3n ?
La taille du "programme " que j'ai utilisé se mesure probablement en téra-octets. Peut-on écrire, et maintenir, un tel programme? Non.

1.3. Développement incrémental

Les connaissances que nous mettons en oeuvre pour résoudre des problèmes sont de deux ordres : les connaissances "noir sur blanc", qu'on trouve par exemple dans les livres, et les connaissances "matière grise". Ces dernières ont la particularité d'être inexprimables, dans la mesure où la personne qui les détient ne sait pas qu'elle les détient. Si par exemple vous demandez à un bon joueur comment il a trouvé tel coup génial, il vous répondra probablement : <<Bein, euh... je ne sais pas ; j'ai regardé l'échiquier, et il m'a semblé qu'il n'y avait rien d'autre à faire>>.
La situation est donc déséspérée? Non, car ces connaissances ne sont pas innées, elles ont été acquises. Reste à identifier le mécanisme d'acquisition. Pour ce faire, comparons le transfert de la connaissance entre un enseignant et ses étudiants, avec le transfert entre un "maitre" et son apprenti.
noir sur blanc matière grise
peu de temps tout son temps
structuré cas par cas
pratiquement pas de retour feedback
information positive information négative
Nous allons donc nous inspirer de ce processus pour développer notre système. Dans un premier temps, l'"ingénieur de la connaissance" (bof) discute avec l'"expert". Il construit un système initial.
L'"expert" soumet un premier problème au système, et analyse la solution.
Le "cogniticien" (beurk) modifie le système : ajout de connaissances, suppression de choses qui avaient été mal comprises.

On recommence.

Même ce qui vient d'être ajouté est remis en question.
Et on continue ainsi jusqu'à ce que, en moyenne, la solution à n'importe quel problème soit jugée acceptable.

Le processus a convergé, on a capturé la connaissance.
Sauf que ce procédé est impraticable : une étude commandée en 1972 par le DoD a montré que, s'il fallait $75 pour écrire une instruction, il en fallait 4000 pour modifier une instruction. Or ici, la quasi totalité du programme résulte de modifications.

1.4. Représentations déclaratives

Que faire? Rendre les modifications moins couteuses. D'où vient le coût? Du fait que le programme est structuré, donc que lorsqu'on veut modifier une instruction il faut prendre toutes les autres en compte, et répercuter la modification en de nombreux endroits. Ce qu'il faudrait, ce serait pouvoir exprimer les connaissances de manière déclarative, c'est-à-dire indépendamment de leur mode d'emploi, pouvoir dire le "quoi" sans se préoccuper du "comment".
Par analogie avec la Thermodynamique, un programme classique a une faible entropie, alors qu'on en veut une très grande ; au lieu d'un cristal, on voudrait un programme "gazeux".
Il existe un langage qui permet cela, connu depuis 2400 ans, qui s'appelle la Logique. C'est pour cette raison que nous allons étudier la Logique, ou plus exactement les Logiques.
Chapitre suivant Table des matières
© Jean-Marc Fouet, Juillet 1999
Attention, ce fichier n'est peut-être plus d'actualité s'il est dans votre cache ; vérifiez la date du copyright, et faites éventuellement un 'reload'.
© Jean-Marc Fouet, 18-11-1999