[Haskell-cafe] ANNOUNCE: monad-control-0.3
Michael Snoyman
michael at snoyman.com
Tue Dec 6 15:34:06 CET 2011
On Tue, Dec 6, 2011 at 3:03 PM, Bas van Dijk <v.dijk.bas at gmail.com> wrote:
> On 6 December 2011 12:59, Michael Snoyman <michael at snoyman.com> wrote:
>> On Tue, Dec 6, 2011 at 11:49 AM, Bas van Dijk <v.dijk.bas at gmail.com> wrote:
>>> On 6 December 2011 05:06, Michael Snoyman <michael at snoyman.com> wrote:
>>>> Maybe this will help[1]. It's using RWST instead of StateT, but it's
>>>> the same idea.
>>>>
>>>> [1] https://github.com/yesodweb/yesod/commit/7619e4e9dd88c152d1e00b6fea073c3d52dc797f#L0R105
>>>
>>> Hi Michael,
>>>
>>> Note that you can just reuse the MonadTransControl instance of the
>>> RWST transformer:
>>>
>>> instance MonadTransControl (GGWidget master) where
>>> newtype StT (GGWidget master) a =
>>> StWidget {unStWidget :: StT (GWInner master) a}
>>> liftWith f = GWidget $ liftWith $ \run ->
>>> f $ liftM StWidget . run . unGWidget
>>> restoreT = GWidget . restoreT . liftM unStWidget
>>>
>>> Cheers,
>>>
>>> Bas
>>
>> Thanks Bas, I was just in the process of converting Widget from being
>> a RWS to a Writer, and your code made it much simpler :).
>>
>> Michael
>
> Do you think it's useful to have the following two utility functions
> for defining a MonadTransControl instance for your own monad
> transformer provided that your transformers is defined in terms of
> another transformer:
>
> defaultLiftWith ∷ (Monad m, MonadTransControl tInner)
> ⇒ (tInner m α → t m α) -- ^ Constructor
> → (∀ β n. t n β → tInner n β) -- ^ Deconstructor
> → (∀ β. StT tInner β → StT t β) -- ^ State constructor
> → ((Run t → m α) → t m α)
> defaultLiftWith con deCon st = \f → con $ liftWith $ \run →
> f $ liftM st ∘ run ∘ deCon
>
> defaultRestoreT ∷ (Monad m, MonadTransControl tInner)
> ⇒ (tInner m α → t m α) -- ^ Constructor
> → (StT t α → StT tInner α) -- ^ State deconstructor
> → (m (StT t α) → t m α)
> defaultRestoreT con unSt = con ∘ restoreT ∘ liftM unSt
>
> For example in your case you would use these as follows:
>
> instance MonadTransControl (GGWidget master) where
> newtype StT (GGWidget master) a =
> StWidget {unStWidget :: StT (GWInner master) a}
> liftWith = defaultLiftWith GWidget unGWidget StWidget
> restoreT = defaultRestoreT GWidget unStWidget
>
> Bas
I don't have a strong opinion, but it sounds like a net win, assuming
the documentation clearly explains how they are supposed to be used.
Michael
More information about the Haskell-Cafe
mailing list