The instance is defined as
instance MonadFix [] where
mfix f = case fix (f . head) of
[] -> []
(x:_) -> x : mfix (tail . f)
But I'm failing to grasp the intuitive meaning behind it with respect to the []
monad seen as non-deterministic computations. In mfix f
function f
must not be strict in its argument, so it can't examine the argument. And according to the definition it also can't use the argument anywhere in its output, otherwise at some point it'll hit fix (f . head)
and diverge. So is there any use (or good example) for mfix
for lists, other than mfix (const someList)
?
It's probably easiest to say it like this. The functions
f
for whichmfix f
is totally defined are those for which the spine off x
does not depend onx
, so they can be written in the formfor some
n
(possibly infinity) and somef1
, ...,fn
. Then(of course for this to really be totally defined, each
fix fi
must also be defined).mfix
can be thought of as nondeterministically giving you the fixed point of a nondeterministic function. The rather heavy restriction is that the shape of the nondeterministic computation cannot depend in any way on the input. We seem to need some kind of restriction on the computation in order to get started, but you might hope to at least be able to kill off a branch of the computation conditionally (say if some intermediate calculation is negative). I've always thought that it should be possible to usemfix
in this way by using a different nondeterminism monad whose choice operation is not associative, but never worked out the details.