I'm intrigued by the construction described [here](https://stackoverflow.com/a/24844388/2684007) for determining a monad transformer from adjoint functors. Here's some code that summarizes the basic idea:

```
{-# LANGUAGE MultiParamTypeClasses #-}

import           Control.Monad

newtype Three g f m a = Three { getThree :: g (m (f a)) }

class (Functor f, Functor g) => Adjoint f g where
  counit :: f (g a) -> a
  unit   :: a -> g (f a)

instance (Adjoint f g, Monad m) => Monad (Three g f m) where
  return  = Three . fmap return . unit
  m >>= f = Three $ fmap (>>= counit . fmap (getThree . f)) (getThree m)

instance (Adjoint f g, Monad m) => Applicative (Three g f m) where
  pure  = return
  (<*>) = ap

instance (Adjoint f g, Monad m) => Functor (Three g f m) where
  fmap = (<*>) . pure

```

Given that `Adjoint ((,) s) ((->) s)`, `Three ((->) s) ((,) s)` appears equivalent to `StateT s`.

Very cool, but I am puzzled by a couple things:

* How can we upgrade a monadic `m a` into a monadic `Three g f m a`? For the specific case of `Three ((->) s) ((,) s)`, it's of course obvious how to do this, but it seems desirable to have a recipe that works for any `Three g f` provided that `Adjoint f g`. In other words, it seems like there should be an analog of `lift` whose definition only requires `unit`, `counit`, and the `return` and `>>=` of the input monad. But I cannot seem to find one (I have seen [a definition using `sequence`](https://github.com/ekmett/adjunctions/blob/master/src/Control/Monad/Trans/Adjoint.hs), but this seems a bit like cheating since it requires `f` to be `Traversable`).
* For that matter, how can we upgrade `g a` into a `Three g f m a` (provided `Adjoint f g`)? Again, for the specific case of `Three ((->) s) ((,) s)` it's obvious how to do this, but I'm wondering if there's an analog of `gets` that only requires `unit`, `counit`, and the `return` and `>>=` of the input monad.