2011-12-18 8 views
7

Estoy cambiando de Haskell a OCaml pero estoy teniendo algunos problemas. Por ejemplo, necesito una definición de tipo para expresiones regulares. Lo hago con:OCaml: circularidad entre el tipo de variante y la definición del módulo

type re = EmptySet 
    | EmptyWord 
    | Symb of char 
    | Star of re 
    | Conc of re list 
    | Or of (RegExpSet.t * bool) ;; 

Los elementos dentro de la O se encuentran en un conjunto (RegExpSet), por lo defino siguiente (y también una función de mapa):

module RegExpOrder : Set.OrderedType = 
    struct 
     let compare = Pervasives.compare 
     type t = re 
    end 
module RegExpSet = Set.Make(RegExpOrder)  
module RegExpMap = Map.Make(RegExpOrder) 

Sin embargo, cuando lo haga "ocaml [nombre del archivo]" consigo:

Error: Unbound module RegExpSet 

en la línea de "O" en la definición de "re".

Si yo cambiaré estas definiciones, es decir, si escribo las definiciones de los módulos antes de que las definiciones de tipo de re obviamente sale:

Error: Unbound type constructor re 

en la línea de "tipo t = re".

¿Cómo puedo solucionar esto? Gracias!

Respuesta

9

Puede intentar usar recursive modules. Por ejemplo, las siguientes compilaciones:

module rec M : 
sig type re = EmptySet 
    | EmptyWord 
    | Symb of char 
    | Star of re 
    | Conc of re list 
    | Or of (RegExpSet.t * bool) 
end = 
struct 
    type re = EmptySet 
    | EmptyWord 
    | Symb of char 
    | Star of re 
    | Conc of re list 
    | Or of (RegExpSet.t * bool) ;; 
end 

and RegExpOrder : Set.OrderedType = 
    struct 
     let compare = Pervasives.compare 
     type t = M.re 
    end 
and RegExpSet : (Set.S with type elt = M.re) = Set.Make(RegExpOrder) 
+0

¡Gracias por responder! Agregué esa definición al principio de mi archivo. Sin embargo, ahora tengo un nuevo problema que es cuando trato de hacer una coincidencia de patrones de argumentos de una función con elementos del tipo M.re. Por ejemplo, esta función let lf exp = coincide con exp con \t M.EmptyWord -> M.EmptySet ;; me da Error: constructor de consolidar M.EmptyWord Ricardo Almeida – vegetus

+0

La implementación de tipo 're' se ha hecho abstracto. Intente eliminar la firma del módulo 'sig type re end'. También busque en los tipos "privados", que permitirán un nivel intermedio de ocultación; fuera del módulo, tendrás que usar constructores especiales para obtener valores de tipo 're', pero igual puedes emparejar el patrón. –

+0

@ user1104586 He actualizado mi respuesta para hacer visibles los constructores de 'M.re'. –

Cuestiones relacionadas