Automates finis et langages
Un algorithme est réalisé dans le but de résoudre un problème. Nous commençons donc logiquement par introduire une formalisation des problèmes en termes de langages, puis nous formalisons la notion d'algorithme par les automates finis.
Formalisation de la notion de problème
Les seuls problèmes abordés ici seront les problèmes de décision. Ceux-ci
admettent uniquement 2 réponses : oui ou non. Un problème de décision est donné
par un ensemble d'instances, partitionné en l'ensemble des
instances positives et l'ensemble des instances négatives.
Nous définissons alors une instance d'un problème de décision qui pose la
question pour un élément particulier de . Toute instance admet une
réponse, qui est positive lorsque et négative lorsque
.
En informatique, il existe d'autres problèmes d'intérêt que les problèmes de décision. Cependant, tout problème peut s'exprimer sous la forme d'un problème de décision. Cette approche permet de définir une théorie du calcul dans un cadre simple et unique. C'est pourquoi nous nous plaçons dans ce cadre.
La notion de problème est indépendante de la notion d'algorithme. Un algorithme peut résoudre un problème, mais il ne le définit pas. Par ailleurs, un problème soluble l'est généralement par plusieurs algorithmes.
Les langages
Un algorithme est déterminé pour résoudre un problème donné. Cependant, toute question qui lui est soumise est une instance de ce problème. Il est donc nécessaire de disposer d'un encodage des instances de problèmes afin de les fournir aux algorithmes. D'une façon générale, une instance d'un problème est représentée par une séquence de symboles.
Un alphabet est un ensemble fini et non vide de symboles, un alphabet
est généralement désigné par .
Un mot sur un alphabet est une séquence finie de symboles de
.
La longueur d'un mot avec est définie par .
Le mot vide, noté , est le mot de longueur nulle : .
La concaténation de deux mots sur
, et sur , est définie
par le mot
sur . La longueur de est donnée par
.
Un mot est un facteur de s'il existe deux mots
et tels que . Un facteur est
propre si (certains auteurs imposent aussi ). Nous appelons préfixe de tout
facteur tel que , i.e. .
Symétriquement, un suffixe de est un facteur tel
que , i.e. .
Un langage sur un alphabet est un ensemble fini ou infini de mots
sur , c'est-à-dire une partie de (ensemble de tous les mots sur ).
Attention à ne pas confondre le langage vide , et le langage contenant uniquement le mot vide .
Représentation d'un problème par un langage
Chaque instance est modélisée par un mot . L'ensemble des instances est alors représenté par le langage des mots qui les encodent. Notons que la description, et non pas la définition, de l'ensemble des instances positives et de l'ensemble des instances négatives dépend de l'encodage choisi.
Automates finis
Nous savons maintenant comment représenter un problème de décision par un langage sur un alphabet choisi : l'ensemble de ses instances , chacune d'elles représentée par un mot sur cet alphabet. L'ensemble des instances positives est lui aussi représenté par un langage , tout comme l'ensemble des instances négatives qui est représenté par le complémentaire de dans . Un algorithme qui résout un problème donné prend en entrée une instance particulière et doit décider si , c'est-à-dire si . Pour cela, l'algorithme doit lire certains symboles du mot qui lui permettent de prendre sa décision. Un modèle d'algorithme ou modèle de calcul doit donc permettre de lire un mot en entrée, de mémoriser certaines informations et de prendre des décisions pour in fine décider si .
Nous introduisons maintenant les automates finis comme modèle de calcul. Un automate fini lit le mot d'entrée , symbole par symbole, de gauche à droite et sans pouvoir revenir en arrière. L'automate est une machine à états qui en représentent la mémoire. L'état de l'automate change pour refléter l'information qu'il mémorise en fonction des symboles de qu'il lit. Il possède certains états particuliers. Les états initiaux correspondent aux connaissances élémentaires qu'il possède avant de lire . Les états accepteurs correspondent aux connaissances permettant de décider si . C'est-à-dire que si, après avoir lu , l'automate se trouve dans un état accepteur, alors est accepté, c'est-à-dire .
Un automate fini est défini par :
- est un ensemble fini d'états
- est l'alphabet de
- est la relation de transition
- est l'ensemble des états initiaux
- est l'ensemble des états accepteurs
Notons qu'en présence d'une transition étiquetée l'automate change d'état sans lire aucun symbole du mot d'entrée. Nous en verrons les conséquences au chapitre 5.
Un automate fini est complet si pour tout et pour tout il existe tel que .
Un automate fini complet possède une transition pour chaque lettre de l'alphabet depuis tout état. Il peut donc traiter tout mot d'entrée entièrement, sans jamais être bloqué avant d'avoir lu l'intégralité du mot d'entrée. Cependant, cela ne suffit pas pour pouvoir programmer l'automate. Il faut de plus que celui-ci soit déterministe, c'est-à-dire que, connaissant l'état de l'automate et la lettre lue, il doit être possible de déterminer l'état suivant de manière unique.
Un automate fini est déterministe si et seulement
si
- il possède un unique état initial :
- il n'existe pas de transition étiquetée :
- et pour tout état , pour tout , il existe au plus un état tel que
Langage accepté
Un automate fini est appliqué à un mot d'entrée donné, encodé dans l'alphabet de l'automate. C'est-à-dire que l'automate, à partir d'un état initial, lit le mot d'entrée lettre à lettre et il franchit, pour chacune d'elles, une transition de même étiquette. Cela définit une exécution de l'automate fini.
Une exécution d'un automate fini sur un mot
d'entrée est une séquence finie de transitions de , avec et
(les valant ne contribuent pas au mot).
Un automate fini déterministe admet donc au plus une exécution pour tout mot d'entrée. A contrario, un automate fini complet (ayant au moins un état initial) admet au moins une exécution pour tout mot d'entrée. Finalement, un automate fini déterministe et complet admet exactement une exécution pour tout mot d'entrée.
Une exécution d'un automate fini pour un mot d'entrée aboutit dans un état donné, ici . C'est alors que l'automate rend une décision : soit est accepteur et alors est accepté, soit au contraire n'est pas accepteur et le mot est rejeté.
Le langage accepté par un automate fini est
l'ensemble des mots pour lesquels il existe une exécution de
qui aboutit dans un état accepteur : .