2017-01-15 3 views
1

Je suis en train d'inverser une liste SML avec la mise en œuvre suivanteSML: inférence de type donnant étrange erreur tout en ajoutant un élément à une liste

fun reverse x y = 
     case x of 
     [] => y 
     | x::xs => reverse(xs, x::y) 
; 

Les messages d'erreur que je reçois est impénétrable:

trial.sml:1.6-4.35 Error: case object and rules don't agree [tycon mismatch] 
    rule domain: 'Z list * 'Z list 
    object: ('Z list * 'Z list) * 'Y 
    in expression: 
    (case (arg,arg) 
     of (x,y) => 
      (case x 
      of nil => y 
       | :: <pat> => reverse <exp>)) 
trial.sml:1.6-4.35 Error: right-hand-side of clause doesn't agree with function result type [tycon mismatch] 
    expression: 'Z -> _ 
    result type: 'Y list 
    in declaration: 
    reverse = (fn arg => (fn <pat> => <exp>)) 

Toutefois, si je change la signature pour être amusant inverse (x: 'une liste, y:' une liste) alors ça marche pourquoi est-ce le cas? Y at-il un moyen d'écrire ceci afin que je n'ai pas besoin d'écrire le type 'une liste?

Répondre

1

x y diffère de (x,y).

Dans la première ligne de la définition

fun reverse x y = 

Vous semblez essayer d'écrire une fonction cari de type

fn: a' list -> a' list -> 'a list 

mais dans l'appel récursif

reverse(xs, x::y) 

vous traitez reverse comme si elle étaient et uncurried fonction du type

fn: une « liste * une » liste -> « une liste

Le problème n'a rien à voir avec vous ajoutez ou non une annotation de type mais il a à voir avec où vous mettez des parenthèses (et des virgules, le cas échéant). Il existe deux correctifs valides en fonction de ce que vous voulez que le type soit. Puisque cela semble être des devoirs (il n'y a pas de raison évidente de non-devoirs pour éviter le rev intégré), je vous laisserai les détails.

+0

oh !! Noo im wasnt intention d'écrire une fonction curry Je vois pourquoi il devient confus. Je ne savais pas que les accents et les virgules faisaient la différence. Merci de votre aide. – Har