2011-11-04 20 views
7

me escribió la siguiente función:GHC rechaza el código de mónada de ST como incapaz de unificar variables de tipo?

(.>=.) :: Num a => STRef s a -> a -> Bool 
r .>=. x = runST $ do 
v <- readSTRef r 
return $ v >= x 

pero cuando intenté compilar me dieron el siguiente error:

Could not deduce (s ~ s1) 
from the context (Num a) 
    bound by the type signature for 
      .>=. :: Num a => STRef s a -> a -> Bool 
    at test.hs:(27,1)-(29,16) 
    `s' is a rigid type variable bound by 
     the type signature for .>=. :: Num a => STRef s a -> a -> Bool 
     at test.hs:27:1 
    `s1' is a rigid type variable bound by 
     a type expected by the context: ST s1 Bool at test.hs:27:12 
Expected type: STRef s1 a 
    Actual type: STRef s a 
In the first argument of `readSTRef', namely `r' 
In a stmt of a 'do' expression: v <- readSTRef r 

¿Alguien puede ayudar?

Respuesta

12

Esto es exactamente como se pretendía. Un STRef solo es válido en una ejecución de runST. Intenta poner un STRef externo en una nueva ejecución de runST. Eso no es valido Eso permitiría efectos secundarios arbitrarios en código puro.

Entonces, lo que intentas es imposible de lograr. ¡Por diseño!

7

que necesita para mantenerse dentro del contexto ST:

(.>=.) :: Ord a => STRef s a -> a -> ST s Bool 
r .>=. x = do 
v <- readSTRef r 
return $ v >= x 

(Y como señala Hammar, utilizar >= que necesita la clase de tipos Ord, que Num no proporciona.)

+1

Tenga en cuenta que este todavía no se escribirá check, ya que la restricción debería ser 'Ord', no' Num'. – hammar

+0

Gracias por detectar eso. – dave4420

Cuestiones relacionadas