Why is ST designed to disallow the following code as shown in the wikibook? The article seems to suggest that ST effects would leak into another ST if this was allowed, but I don't really understand why.
It seems that I cannot run a specific ST s (STRef s a). Are ST effects contained and referentially transparent, but such use is still considered invalid?
Intuition tells me that there is difference between semantics of IO and ST related to that there is one IO and many independent ST, but I'm not sure.
> runST (newSTRef True)
<interactive>:5:8: error:
• Couldn't match type ‘a’ with ‘STRef s Bool’
because type variable ‘s’ would escape its scope
This (rigid, skolem) type variable is bound by
a type expected by the context:
forall s. ST s a
at <interactive>:5:1-21
Expected type: ST s a
Actual type: ST s (STRef s Bool)
• In the first argument of ‘runST’, namely ‘(newSTRef True)’
In the expression: runST (newSTRef True)
In an equation for ‘it’: it = runST (newSTRef True)
• Relevant bindings include it :: a (bound at <interactive>:5:1)
> :t newSTRef
newSTRef :: a -> ST s (STRef s a)
> :t runST
runST :: (forall s. ST s a) -> a