Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Clarify role of list monad operator

I came across a Haskell function that tells whether a list is sorted, and I'm having trouble understanding how it works.

The code in question is

f = zipWith (<=) <*> tail

which I understand to be equivalent (in point-ful style) to

f' xs = zipWith (<=) xs (tail xs)

and as an example returns

f [4, 5, 1] == [True,False]

I take it that it has something to do with the list monad and sequential application, but would appreciate if someone could make the meaning more clear to me. What exactly is <*> doing here?

like image 869
beardc Avatar asked May 30 '14 17:05

beardc


1 Answers

The <*> here isn't acting on the [a] applicative, it's acting in the (->) a applicative instance.

Essentially

 instance Applicative ((->) a) where
   pure = const -- same as monadic return
   f <*> a = \x -> f x (a x)

So it acts like function application, but also wraps the application in a function and gives the argument to both sides.

So expanding your function

 zipWith (<=) <*> tail
 \x -> zipWith (<=) x (tail x)
 \(x:xs) -> zipWith (<=) (x:xs) xs

In general it's correct to view <*> as just function application + some extra goodies. You can almost read it as whitespace!

like image 52
Daniel Gratzer Avatar answered Oct 11 '22 10:10

Daniel Gratzer