Nous avons apporté une réponse formelle à la
verbosité de la notation sous la forme d'une procédure
qui complète les notations de type
manquantes [Louvet et Ridoux 96, Louvet 96].
Elle permet d'omettre la plupart des notations de type,
pour les laisser reconstituer par un compilateur.
L'intuition que l'inférence de type au second ordre n'est pas
faisable semble contredire la possibilité de cette complétion.
En effet,
au second ordre, il n'y a pas de type principal,
et après une longue période
où on ne savait pas si le problème d'inférence était décidable
[Leivant 83, Mitchell 84, Pierce et al. 89]
Wells a prouvé que ce problème ne l'était
pas [Wells 94].
En fait,
la complétion proposée n'a pas pour but de résoudre
complètement l'inférence de type au second ordre :
comme en Prolog, les types des constantes et des prédicats doivent être donnés,
et les
-quantifications inférées sont toutes prénexes.
Par exemple,
partant des déclarations suivantes,
type p A -> B -> (paire A B) .
type appliquer_à_paire
appliquer_à_paire F (p G D) (p ([F TypeG] G) ([F TypeD] D)) .
D(D->D) -> (paire A B) -> (paire A B) -> o .
la complétion reconstitue d'abord les manquants
dans les déclarations de type,
type p
type appliquer_à_paire
A
B( A -> B -> (paire A B) ) .
A
B(
D(D->D) -> (paire A B) -> (paire A B) -> o ) .
puis les applications de type dans les clauses,
[appliquer_à_paire TypeG TypeD]
F
([p TypeG TypeD] G D)
([p TypeG TypeD]([F TypeG] G) ([F TypeD] D)) .
et enfin les quantifications manquantes, en distinguant les quantifications
de variables de terme, , et les quantifications de variables de
type,
.
TypeG
TypeD
D:TypeD
G:TypeG
F:
D(D->D)
([appliquer_à_paire TypeG TypeD]
F
([p TypeG TypeD] G D)
([p TypeG TypeD]([F TypeG] G) ([F TypeD] D))) .
On peut constater que les variables de types qui décoraient les deux applications de la fonction F ont été dupliquées comme paramètres de appliquer_à_paire et p. C'est ce qui va permettre la propagation des informations de type jusqu'aux points que le programmeur a explicitement annoté dans le source du programme.
La procédure de complétion permet de convertir au polymorphisme paramétrique
tous les programmes Prolog.
Cependant,
tous les programmes paramétriques ne sont pas accessibles par complétion
d'un programme
Prolog.
Par exemple,
le prédicat pred_ad_hoc n'a pas de version purement
Prolog
(avec condition de tête).
En fait,
les programmes qui implémentent du polymorphisme ad-hoc ne
peuvent pas être atteints par complétion d'un programme
Prolog vérifiant la condition de tête.
Par exemple,
type plus A -> A -> A -> o .
type conc (list A) -> (list A) -> (list A) -> o .
[plus A] X Y Z :-
( A = int ==> Z = X + Y
; A = (list B) ==> conc X Y Z ) .
est complété en le programme suivant,
type plus
type conc
A( A -> A -> A -> o ) .
A( (list A) -> (list A) -> (list A) -> o ) .
A
B
X:A
Y:A
Z:A
[plus A] X Y Z :-
( A = int ==> [= A] Z (X + Y)
; A = (list B) ==> [conc B] X Y Z ) .
mais on ne peut pas se passer de mentionner les variables de type A et B dans la version abrégée du programme.