I tried writing down joinArr :: ??? a => a r (a r b) -> a r b
.
I came up with a solution which uses app
, therefore narrowing the a
down to ArrowApply
's:
joinArr :: ArrowApply a => a r (a r b) -> a r b
joinArr g = g &&& Control.Category.id >>> app
Is it possible to have this function written down for arrows?
My guess is no.
Control.Monad.join
could have been a good stand-in for >>=
in the definition of the Monad
type class: m >>= k = join $ k <$> m
.
Having joinArr :: Arrow a => a r (a r b) (a r b)
on our hands, it would be possible to write down instance Arrow a => Monad (ArrowMonad a)
:
m >>= k = joinArr (k <$> m)
Please note that joinArr
should be slightly tweaked to be able to deal with the wrapper. If we speak of ArrowApply
:
joinArr :: ArrowApply a => ArrowMonad a (ArrowMonad a b) -> ArrowMonad a b
joinArr (ArrowMonad m) = ArrowMonad $
m &&& Control.Category.id >>>
first (arr (\x -> let ArrowMonad h = x in h)) >>>
app
instance ArrowApply a => Monad (ArrowMonad a)
is already implemented in the source file.
I reckon this argument not to be the best one (if it is right).
Am I right? What is the more formal way to back this up (or disprove it)?
Arrow
is aMonad
. – Joseph Sible-Reinstate MonicaArrow
does not give rise to aMonad
generally. Yet I reckonjoinArr :: Arrow a => a r (a r b) -> a r b
to enable us to write this down. Or am I using this fact wrongly? – Zhiltsoff IgorjoinArr
, then you could writeinstance Monad SomeArrowThatIsntAMonad where m >>= f = joinArr (f <$> m)
. – Joseph Sible-Reinstate Monica(.)
,id
,arr
andfirst
, there isn't anything that allows collapsing twoa r
layers into one. (2) @JosephSible-ReinstateMonica It's not a particularly enlightening example, perhaps, butStatic
for any applicative which isn't a monad should suffice.Scan
from the foldl library might be a more interesting illustration. – duplode