<div dir="ltr">On Mon, Nov 28, 2016 at 4:41 PM, wren romano <span dir="ltr"><<a href="mailto:wren@community.haskell.org" target="_blank">wren@community.haskell.org</a>></span> wrote:<br><div class="gmail_extra"><div class="gmail_quote"><blockquote class="gmail_quote" style="margin:0px 0px 0px 0.8ex;border-left-width:1px;border-left-color:rgb(204,204,204);border-left-style:solid;padding-left:1ex">I'd much rather see the above functions as:<br>
<br>
    mapMaybes :: Foo f => (a -> Maybe b) -> f a -> f b<br>
    catMaybes :: Foo f => f (Maybe a) -> f a<br></blockquote><div> </div><div>A while back, I found myself deriving this class:</div><div><br></div><div><div><div>    class Functor f => Siftable f where</div><div>        siftWith :: (a -> Maybe b) -> f a -> f b</div><div>        sift :: (a -> Bool) -> f a -> f a</div><div>        sift f = siftWith (\a -> if f a then Just a else Nothing)</div></div></div><div><br></div><div>which is essentially Witherable minus Traversable. It has the nice property that it’s a functor from the Kleisli category for Maybe to Hask, so the laws are intuitive and easily expressed. You can even express wither using siftWith and traverse</div><div><br></div><div><div>    wither :: (Siftable t, Traversable t, Applicative f) => (a -> f (Maybe b)) -> t a -> f (t b)</div><div>    wither f = fmap (siftWith id) . traverse f</div></div><div><br></div><div>But it turns out that there aren’t many instances of Siftable that aren’t also Traversable. The most obvious would be infinite streams, but even they have a traversal if you restrict yourself to lazy applicatives.</div></div><div><br></div>-- <br><div class="gmail_signature">Dave Menendez <<a href="mailto:dave@zednenem.com" target="_blank">dave@zednenem.com</a>><br><<a href="http://www.eyrie.org/~zednenem/" target="_blank">http://www.eyrie.org/~zednenem/</a>></div>
</div></div>