Help In Understanding These Statesments In Haskell - haskell

What is the meaning of these statements in Haskell:
a)
(\x -> x + 1)
b)
(\x -> x - 2)
c)
(\x -> mod (x * 3) 5)
I understand the x + 1, mod(x * 3) 5 etc but the \x before those statements makes them difficult for me to understand.
thanks for your help

\ and -> define a lambda (you could call it an inline function or a nameless function). So \x->x is the same as \ x -> x is the same as a function which returns its argument. And \x y -> x + y is a function which returns the sum of its two arguments.

Related

Currying in Haskell with 2+ arguments

I'm starting to learn Haskell so I need to understand currying also (it's the first time I've seen this technique too). I think I get how it works in some cases where the currification only "eliminates" one of the parameters. Like in the next example where I'm trying to calculate the product of 4 numbers.
This is the uncurried function:
prod :: Integer->Integer->Integer->Integer->Integer
prod x y z t = x * y * z * t
This is the curried function:
prod' :: Integer->Integer->Integer->Integer->Integer
prod' x y z = (*) (x*y*z)
But I don't understand how could I continue this dynamic and do for example the same function with only two arguments and so on:
prod'' :: Integer->Integer->Integer->Integer->Integer
prod'' x y =
This is the uncurried function:
prod :: Integer -> Integer -> Integer -> Integer -> Integer
prod x y z t = x * y * z * t
This is already a curried function. In fact all functions in Haskell are automatically curried. Indeed, you here wrote a function that looks like:
prod :: Integer -> (Integer -> (Integer -> (Integer -> Integer)))
Haskell will thus produce a function that looks like:
prod :: Integer -> (Integer -> (Integer -> (Integer -> Integer)))
prod = \x -> (\y -> (\z -> (\t -> x * y * z * t)))
Indeed, we can for example generate such function:
prod2 = prod 2
This will have type:
prod2 :: Integer -> (Integer -> (Integer -> Integer))
prod2 = prod 2
and we can continue with:
prod2_4 :: Integer -> (Integer -> Integer)
prod2_4 = prod2 4
and eventually:
prod2_4_6 :: Integer -> Integer
prod2_4_6 = prod2_4 6
EDIT
The function prod' with:
prod'' x y = (*) ((*) (x*y))
Since that means you multiply (*) (x*y) with the next parameter. But (*) (x*y) is a function. You can only multiply numbers. Strictly speaking you can make functions numbers. But the Haskell compiler thus complains that:
Prelude> prod'' x y = (*) ((*) (x*y))
<interactive>:1:1: error:
• Non type-variable argument in the constraint: Num (a -> a)
(Use FlexibleContexts to permit this)
• When checking the inferred type
prod'' :: forall a.
(Num (a -> a), Num a) =>
a -> a -> (a -> a) -> a -> a
It thus says that you here aim to perform an operation with a function a -> a as first operand, but that this function is not an instance of the Num typeclass.
What you have is
prod x y z t = x * y * z * t
= (x * y * z) * t
= (*) (x * y * z) t
Hence by eta reduction (where we replace foo x = bar x with foo = bar)
prod x y z = (*) (x * y * z)
= (*) ( (x * y) * z )
= (*) ( (*) (x * y) z )
= ((*) . (*) (x * y)) z
so that by eta reduction again,
prod x y = (*) . (*) (x * y)
Here (.) is the function composition operator, defined as
(f . g) x = f (g x)
What you're asking about is known as point-free style. "Point-free" means "without explicitly mentioning the [implied] arguments" ("point" is a mathematician's jargon for "argument" here).
"Currying" is an orthogonal issue, although Haskell being a curried language makes such definitions -- and partial application ones, shown in Willem's answer -- easier to write. "Currying" means functions take their arguments one at a time, so it is easy to partially apply a function to a value.
We can continue the process of pulling the last argument out so it can be eliminated by eta reduction further. But it usually rapidly leads to more and more obfuscated code, like prod = ((((*) .) . (*)) .) . (*).
That's because written code is a one-dimensional encoding of an inherently two-dimensional (or even higher-dimensional) computational graph structure,
prod =
/
*
/ \
*
/ \
<-- *
\
You can experiment with it here. E.g., if (*) were right-associative, we'd get even more convoluted code
\x y z t -> x * (y * (z * t))
==
(. ((. (*)) . (.) . (*))) . (.) . (.) . (*)
representing just as clear-looking, just slightly rearranged, graph structure
/
<-- *
\ /
*
\ /
*
\

Haskell `let` bindings in lambda calculus

I want to understand how let bindings work in Haskell (or maybe lambda calculus, if the Haskell implementation differs?)
I understand from reading Write you a Haskell that this is valid for a single let binding.
let x = y in e == (\x -> e) y
This makes sense to me, since it's consistent with how bindings work in the lambda calculus. Where I'm confused is using multiple let bindings, where one binding can reference the bindings above. I will provide a trivial example.
Original code:
let times x y = x * y
square x = times x x
in square 5
My guess at the implementation:
(\square times -> square 5) (\x -> times x x) (\x -> x * x)
This seems not to work because times is not defined when square is called by the lambda. However, this can by solved by this implementation:
(\square -> square 5) ((\times x -> times x x) (\x -> x * x))
Is this the proper way to implement this binding, at least in the lambda calculus?
The times/square example can be expressed in terms of lambda functions using scoping:
(\times -> (\square -> square 5)(\x -> times x x))(\x y -> x * y)
But scoping isn't enough for recursive or mutually recursive let-bindings like
let ones = 1 : ones in take 5 ones
let even n = n == 0 || odd (abs n - 1)
odd n = n /= 0 && even (abs n - 1)
in even 7
In the lambda calculus you can define the y-combinator for recursion as
(\f -> (\x -> f (x x))(\x -> f (x x)))
This lets you define functions and values in terms of themselves. That formulation isn't legal haskell due to typing constraints but there are ways around that.
Using the y-combinator lets us express the above let-bindings using the lambda calculus:
(\ones -> take 5 ones)((\f -> (\x -> f (x x))(\x -> f (x x)))(\ones -> 1 : ones))
(\evenodd -> evenodd (\x y -> x) 7)((\f -> (\x -> f (x x))(\x -> f (x x)))(\evenodd c -> c (\n -> n == 0 || evenodd (\x y -> y) (abs n - 1)) (\n -> n /= 0 && evenodd (\x y -> x) (abs n - 1))))
Note that multiple let bindings can be reduced to a single one, defining a pair (tuple, in the general case). E.g. we can rewrite
let times x y = x * y
square x = times x x
in square 5
as
let times = \x y -> x * y
square = \x -> times x x
in square 5
then
let (times, square) = (\x y -> x * y, \x -> times x x)
in square 5
then, if wanted,
let pair = (\x y -> x * y, \x -> fst pair x x)
in snd pair 5
After that, we can apply the usual lambda calculus translation. If the pair definition ends up to be recursive, as in the case above, we need a fixed point combinator.
(\pair -> snd pair 5) (fix (\pair -> (\x y -> x * y, \x -> fst pair x x)))
Note that this translation does not play along type inference algorithms, which handle let in a special way, introducing polymorphism. This is not important if we only care about the dynamic aspects of our program, though.
I will answer my own question to maybe provide a helpful perspective to those who visit this question.
We want to implement the following program with two let bindings:
let times a b = a * b
square x = times x x
in square 5
To start with, let's simplify this to the essence of what we want:
square 5
Simple enough. However, square in this case is undefined! Well, we can bind it using the mechanism our language provides us with - a lambda. This gives us (\ square -> square 5) (\x -> times x x). Now square is defined, but its cousin times is not... Well, we need another lambda! Our final program should look like this:
(\times -> (\square -> square 5) (\x -> times x x)) (\a b -> a * b)
Notice that the (\times -> ...) completely encloses our last step, so that times will be in scope as it is bound. This is consistent with the answer given by #rampion, and reduces as follows:
(\times -> (\square -> square 5) (\x -> times x x)) (\a b -> a * b) =>
(\square -> square 5) (\x -> (\a b -> a * b) x x) =>
(\square -> square 5) (\x -> (\b -> x * b) x) =>
(\square -> square 5) (\x -> x * x) =>
(\x -> x * x) 5 =>
5 * 5 =>
25
If the square function had not depended on times, we could have easily written (\times square -> ..... The dependency means that we must nest these two environments, one containing times, and another inside of that which can use its definition.
Thanks for all of your help! I'm blown away by the simplicity and power of the lambda calculus.

Meaning of different lambda functions and characters

At the moment I am learning Haskell, but I am struggling with the syntax of a few example. What do they exactly mean?
First: What is the difference between these two lambdas (-> \y and y)?
lambda1 = \x -> \y -> x + y
lambda2 = \x y -> x + y
Second: What does this mean? Is this a lambda that act as a "pseudo" list generator that generates a list with 3 elements. How can I create such a list?
lambda3 = [\x -> x+1, \x -> 2*x, \x -> x^2]
Third: What does the \_ exactly mean?
lambda4 = \_ -> (\x -> x+1, \() -> 'a')
lambda2 is syntactic sugar for lambda1. All of these are equivalent:
f = \x -> \y -> x + y
f = \x y -> x + y
f x = \y -> x + y
f x y = x + y
f x y = (+) x y
f x = (+) x
f = (+)
lambda3 is a list of unary functions on numbers. Each function has the type (Num a) => a -> a, so the list has type (Num a) => [a -> a]. You could produce a list of values from this with map or a list comprehension:
fs = [\x -> x+1, \x -> 2*x, \x -> x^2]
map (\f -> f 3) fs
map ($ 3) fs
[f 3 | f <- fs]
==
[4, 6, 9]
lambda4 uses pattern-matching syntax. For example, if you have a data type:
data Foo = Foo Int String
Then you can write a lambda that pattern-matches on it:
f = \ (Foo n s) -> concat (replicate n s)
f (Foo 3 "bar") == "barbarbar"
(But unlike case, there is no way to provide alternative patterns if Foo has multiple constructors.)
The _ pattern just says “accept a value and ignore it”, so lambda4 is a function that accepts an argument, ignores it, and returns a pair (2-tuple) of unary functions, the first of type (Num a) => a -> a and the second of type () -> Char, so its type is Num a => r -> (a -> a, () -> Char).
lambda4 = \_ -> (\x -> x+1, \() -> 'a')
lambda4 = \ignored -> (\x -> x+1, \() -> 'a')
(inc, getA) = lambda4 ()
inc 3 == 4
getA () == 'a'
Functions that ignore their arguments can be constructed with the const function, and operator sections ((+ 1)) are typically preferred over lambdas (\x -> x + 1), so you can also write the above as:
lambda4 = const ((+ 1), const 'a')
On your second question, lambda3 is just a bad variable name. this is a list of functions of type Num a => a -> a. You can verify that by typing the following in ghci:
:t [\x -> x+1, \x -> 2*x, \x -> x^2]
First: What is the difference between these two lambdas (-> \y and y)?
There is no difference. Both produce the same output for the same input, and since they're pure functions, you can be sure that they produce no external effects that you wouldn't see.
The difference lies in that the first lambda uses syntactic sugar for currying.
\x y -> x + y is equal to \x -> \y -> x + y. Now, don't you think it looks a lot like type signatures, such as foo :: Int -> Int -> Int ? ;)
It means that the function foo takes 2 Int and produces an Int.
Since I don't have a very precise answer for the 2nd…
Third: What does the \_ exactly mean?
It's a lambda function (\) to which is associated the _ variable. _ is used as a placeholder to say “I don't care about the content of this variable, I'm even going to give it a proper name”.
There is no -> y. The correct way to read this is
(\ x -> (\ y -> (x + y)))
As it happens, Haskell has "curried functions", which means that
\ x y -> (x + y)
just happens to be equivalent to the above.
lambda3 is a list which contains three elements. Each of those elements happens to be a function. Functions are data in Haskell; you can pass them as arguments, return them as results, stuff them into lists, etc.
lambda3 = [ (\x -> x+1) , (\x -> 2*x) , (\x -> x^2) ]
lambda4 = \_ -> (\x -> x+1, \() -> 'a')
The "_" character basically means "I don't care what this is; ignore it". You can use it anywhere you can use a pattern. For example,
foobar x _ z = x + y
is a 3-argument function that completely ignores argument #2. Read about pattern matching and this should become clear. (I.e., it's not to do with lambdas, it's to do with patterns.)

How to apply a lambda with 2 parameters to a list in Haskell?

In Haskell, I can take the following lambda expression:
\x y -> x * y
and apply it like:
(\x y -> x * y) 9 9
81
(\x y -> x * y) 8 8
64
If I want to express something like, "Take the above lambda, and map it over a list, each item being a pair of values, like above, and return a list, each value being the result of having applied that lambda expression", how can I do it?
In pseudo-code I mean something like: Take (\x y -> x * y) and apply it to something like [(9, 9), (8, 8)].
I know that if I had \x -> x + 1, I can do the following:
map (\x -> x + 1) [9, 9, 9]
[10,10,10]
In other words, I'm trying to find out if it is possible (and how) to do something like
map (\x y -> x * y) [ a list of items, each being a pair of values, on which the lambda can work ]
Apparently, the following doesn't work:
map (\x y -> x * y) [(9, 9), (8, 8)]
it doesn't return [81, 64]. Is there a way to do that?
let list = [(9, 9), (8, 8)]
-- if you want to do it inline
map (\(x, y) -> x * y) list
-- or if you already have a 2 parameter version of a function
let f x y = x * y
uncurry :: (a -> b -> c) -> ((a, b) -> c)
map (uncurry f) list
There's a difference between \(x, y) -> x * y :: (Int, Int) -> Int and \x y -> x * y :: Int -> Int -> Int.
The first is a function that takes one parameter - a tuple and returns the result of multiplication.
The second is a function that takes two parameters and returns the result of multiplication.

Starting with Haskell

Can someone explain to me whats going on in this function?
applyTwice :: (a -> a) -> a -> a
applyTwice f x = f (f x)
I do understand what curried functions are, this could be re-written like this:
applyTwice :: ((a -> a) -> (a -> (a)))
applyTwice f x = f (f x)
However I dont fully understand the (+3) operator and how it works. Maybe it's something really stupid but I can't figure it out.
Can someone explain step by step how the function works? Thanks =)
applyTwice :: ((a -> a) -> (a -> (a)))
applyTwice f x = f (f x)
Haskell has "operator slicing": if you omit one or both of the arguments to an operator, Haskell automatically turns it into a function for you.
Specifically, (+3) is missing the first argument (Haskell has no unary +). So, Haskell makes that expression into a function that takes the missing argument, and returns the input value plus 3:
-- all the following functions are the same
f1 x = x + 3
f2 = (+3)
f3 = \ x -> x + 3
Similarly, if you omit both arguments, Haskell turns it into a function with two (curried) arguments:
-- all the following functions are the same
g1 x y = x + y
g2 = (+)
g3 = \ x y -> x + y
From comments: note that Haskell does have unary -. So, (-n) is not an operator slice, it just evaluates the negative (same as negate n).
If you want to slice binary - the way you do +, you can use (subtract n) instead:
-- all the following functions are the same
h1 x = x - 3
h2 = subtract 3
h3 = \ x -> x - 3

Resources