2012-04-12 9 views
7

Estoy en el proceso de escribir una biblioteca de vectores de juguetes (física) y tengo problemas con las funciones de insistencia de GHC que deberían tener Integer s en su tipo. Quiero vectores para multiplicar vectores, así como escalares (simplemente utilizando *), y si bien esto era posible con sólo tener Vector ejemplo Num Ahora estoy consiguiendo errores del tipo:¿Por qué Haskell inferiría un tipo específico (aparentemente) inconsistentemente?

Couldn't match expected type `Integer' with actual type `Double' 

Después de jugar un poco con el código con el fin de precisar el problema he conseguido que reduce a esto:

data V a = V a a a deriving (Show, Eq, Functor) 
scale a (V i j k) = V (a*i) (a*j) (a*k) 
(<.>) = scale 

Ahora bien, si nos preguntamos qué tipo GHCi estos son obtenemos:

>:t scale 
scale :: Num a => a -> V a -> V a 
>:t (<.>) 
(<.>) :: Integer -> V Integer -> V Integer 

Donde ciertamente no queremos <.> solo actuando en Integer s. Si bien esto se puede solucionar aquí incluyendo una firma de tipo para <.>, me gustaría saber qué está sucediendo realmente.

+0

posible duplicado de [¿Cuál es la restricción de monomorfismo?] (Http://stackoverflow.com/questions/32496864/what-is-the-monomorphism-restriction) – Bakuriu

Respuesta

15

Te encuentras con el infame . Otra solución sería especificar explícitamente argumentos:

a <.> v = scale a v 

O añadir -XNoMonomorphismRestriction pragma.

+0

Tan cerca ... Si tan solo tuviera un compilador Haskell listo: P. –

+15

... o agregue una firma de tipo. Escribir firmas en todas las funciones de nivel superior se considera un buen estilo de todos modos, por lo que esta es mi forma preferida de evitar problemas relacionados con la restricción del monomorfismo. – hammar

Cuestiones relacionadas