Ashley Yakeley wrote: At 2002-02-06 01:09, John Hughes wrote:
>No no no! This still makes the reference type depend on the monad type, which >means that I cannot manipulate the same reference in two different monads! Yes you can. Consider: -- m somehow uses 'rep' internally class (Monad rep, Monad m) => LiftedMonad rep m where { lift :: rep a -> m a; } instance LiftedMonad (ST s) (ST s) where { lift = id; } instance LiftedMonad (ST s) TransformedMonad where ... liftRef :: (LiftedMonad rep m) => Ref rep a -> Ref m a; liftRef ref = ... newSTRef :: a -> Ref (ST s) a; newSTLiftedRef :: (LiftedMonad (ST s) m) => a -> Ref m a; newSTLiftedRef = liftRef . newSTRef; With me so far? Now here's the clever bit: Refs created with newSTLiftedRef are of type '(LiftedMonad (ST s) m) => Ref m a'. This means they will work equally well as 'Ref (ST s) a' as they will as 'Ref TransformedMonad a'. Well, I'm still not convinced. A reference *value* can't have the type (LiftedMonad (ST s) m) => Ref m a This is the type of a function, which given a dictionary returns a reference. Moreover, since when I write do r <- newSTLiftedRef x ... then I am effectively lambda-binding r, then r cannot have this type. It can only have an instance of it ... which ties r to the monad m. Am I missing something here? Seems to me, to do what you're suggesting I would have to put the context inside the Ref type itself: data Ref s a = Ref { readRef :: forall m. LiftedMonad (ST s) m => m a, writeRef :: forall m. LiftedMonad (ST s) m => a -> m () } But now the s had to go back in the type of the reference... Are you really in Seattle? If so, you must be a real nightbird or a tremendously early riser! John _______________________________________________ Haskell mailing list [EMAIL PROTECTED] http://www.haskell.org/mailman/listinfo/haskell