I wrote the following function:
(.>=.) :: Num a => STRef s a -> a -> Bool
r .>=. x = runST $ do
v <- readSTRef r
return $ v >= x
but when I tried to compile I got the following 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
Can anyone help?
This is exactly as intended. An STRef
is only valid in one run of runST
. And you try to put an external STRef
into a new run of runST
. That is not valid. That would allow arbitrary side-effects in pure code.
So, what you try is impossible to achieve. By design!
You need to stay within the ST
context:
(.>=.) :: Ord a => STRef s a -> a -> ST s Bool
r .>=. x = do
v <- readSTRef r
return $ v >= x
(And as hammar points out, to use >=
you need the Ord
typeclass, which Num
doesn't provide.)
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With