- : int LO.result = None
On the other hand, when Option is on the inside, as in LO, failures (which we represent by `mzero`s from the Option monad, here `hoist Monad.Option.mzero`, not the List monad's own `mzero`) abort the whole computation.
+
+This is fun. Notice the difference it makes whether the second `++` is native to the outer `Monad.List`, or whether it's the inner `Monad.List`'s `++` hoisted into the outer wrapper:
+
+ # module LL = Monad.List.T(Monad.List);;
+
+ # LL.(run((++) (mid 1) (mid 2) >>= fun i -> (++) (mid i) (mid (10*i)) ));;
+ - : int LL.result = \[[1; 10; 2; 20]]
+ # LL.(run((++) (mid 1) (mid 2) >>= fun i -> hoist L.((++) (mid i) (mid (10*i)) )));;
+ - : int LL.result = [[1; 2]; [1; 20]; [10; 2]; [10; 20]]
-->
<!--
Exception: Failure "bye".
-->
-This is fun. Notice the difference it makes whether the second `++` is native to the outer `Monad.List`, or whether it's the inner `Monad.List`'s `++` hoisted into the outer wrapper:
-
- # module LL = Monad.List.T(Monad.List);;
-
- # LL.(run((++) (mid 1) (mid 2) >>= fun i -> (++) (mid i) (mid (10*i)) ));;
- - : int LL.result = \[[1; 10; 2; 20]]
- # LL.(run((++) (mid 1) (mid 2) >>= fun i -> hoist L.((++) (mid i) (mid (10*i)) )));;
- - : int LL.result = [[1; 2]; [1; 20]; [10; 2]; [10; 20]]
-
Further Reading