Given
newtype Tree m a = Tree { runTree :: m (Node m a) }
data Node m a = Node
{ nodeValue :: a
, nodeChildren :: [Tree m a]
}
Is there a valid MonadFix
instance?
My attempt was
instance MonadFix m => MonadFix (Tree m) where
mfix f = Tree $ do
Node
<$> mfix (runTree . f . nodeValue)
<*> fmap nodeChildren (runTree (mfix f))
Yet this doesn't seem to terminate when I actually try and use it. The instance is somewhat inspired by the MonadFix
instance for lists.
Monad (Tree m)
look like to begin with? – SwineherdTree
I'm trying to addMonadFix
to. – MatrimonyMonadFix []
: usefix
onf
to grab the shape of the top layer, and generate the subtrees by callingmfix
recursively on the subpositions with a modifiedf
that targets each position precisely. I'm pretty confident that it does the right thing forTree Identity
however I'm not convinced I'm not forcing somem
actions too early wrt what I infer is theTree m
's semantics. – SwineherdnodeValue <$> runTree (mfix (const (return ()))
, which I believe should just be()
(usingreturn
forTree
just creates aNode
with a value and no children). In fact, it actually just blows the stack with a stack overflow exception (how appropriate). – Matrimonym
equal toIO
but I tested it withIdentity
orState Int
and it seems to be working out. I wonder what's special aboutIO
(or whether we can find other failing examples). – Swineherdmfix
ratherfix
, and hencem
must also beMonadFix
. That at least satisfies my above example inIO
. – MatrimonyFreeT []
. Is it? If so, and if the instance you give is valid, under what circumstances canFreeT f m
have a validMonadFix
instance? – Meimeibers