Introduction to Functional Programming
Sébastien BESNIER
What's Functional Programming?
→ Limit Mutations as most a possible






F# (.NET)
Java Virtual Machine
Haskell
PureScript
Elm
ReScript
Byte code
Native
(+to JS)
To JS
(this is ML-family languages,
there's also the LISP family)

Helpful
Compiler
initialModel =
{ count = 0 }
type Msg
= Increment
| Decrement
update msg model =
case msg of
Increment ->
{ model | count = model.count + 1 }
Decrement ->
{ model | count = model.count - 1 }
view model =
div [style "font-size" "200%"]
[ button [ onClick Increment ] [ text "+1" ]
, div [ style "color" "red" ] [ text <| String.fromInt model.count ]
, button [ onClick Decrement ] [ text "-1" ]
]
https://ellie-app.com/fDyHsFVJCska1
Challenge: Reset to 0
Implement a Nim game
https://ellie-app.com/g8qBmxW99x4a1
Rules:
- 10 lucifers at the beginning
- 2 players
- at his turn, the player can take 1,2 or 3 matches
- the player taking the last lucifer lost
No mutation! Only values and pure functions
No mutation! Only values and pure functions
Do you know impure functions?
eight = 5 + 3
Affectation
Try it online

eight = round 8.3
Function call
add a b = a + b
Function definition
add a b = a + b
-- call that function:
eight = add 7 1
Function definition
Challenge
Compute length of \(\texttt{"hello world"}\) and add 5 to it using the \(\texttt{add}\) function (in 1 expresion!)
String.length "abc" -- returns 3
eight = add 7 1
add a b = a + b
Order of declarations does not matter
add : Int -> Int -> Int
add a b = a + b
Types
String.length : ???
What is the type of String.length ?
String.length : String -> Int
What is the type of String.length ?
add3 a b c = a + b + c
What is the type of add3?
add3:
Int
-> Int
-> Int
-> Int
add3 a b c = a + b + c
Good practice:
add type anotation!
String.append "hello " "world"
-- returns "hello world"
What is the type of String.append ?
String.append "hello " "world"
-- returns "hello world"
String.append : String -> String -> String
What is the type of String.append ?
t = add 5 String.append "hey" "hoy"
f a b =
String.length (String.append a b)
g a b =
add (String.append a a) b
h a b =
add (String.append a b) b
What is the type of the following expressions?
user =
{ name = "Seb"
, score = 42
, city = "Paris"
}
Records
user : User
user =
{ name = "Seb"
, score = 42
, city = "Paris"
}
Records
type alias User =
{ name : String
, score : Int
, city : String
}
Records
newUser =
{ user | score = 43 }
newUserBis =
{ user | score = user.score + 1 }
Record updates
newUser : User
newUser =
{ user | score = 43 }
newUserBis : User
newUserBis =
{ user | score = user.score + 1 }
Record updates
rewardUser : User -> User
-- increase the score by one
Record updates
rewardUser : User -> User
rewardUser user =
{ user | score = user.score + 1 }
Record updates
Challenge: add type definition for the model in the counter example
Custom types
Records to store multiple data
(name, score, city....)
Custom types
Records to store multiple data
(name, score, city....)
What about data following various patterns ?
Modeling a shape
Point Circle Float Rectangle Float Float
Radius
Length
Width
What is the type of a shape?
Reminder: counter
type Msg
= Increment
| Decrement
First variant
Second variant
Modeling a shape
Point Circle Float Rectangle Float Float
Radius
Length
Width
Modeling a shape
Point Circle Float Rectangle Float Float
Modeling a shape
type Shape =
Point | Circle Float | Rectangle Float Float
Use a custom type
myRect = Rectangle 10 20
bigCircle = Circle 420000
describe : ???
describe shape =
case shape of
Point ->
"A lonely point"
Circle radius ->
"A circle of radius "
++ String.fromFloat radius
Rectangle width height ->
"A rectangle of area "
++ String.fromFloat (width*height)
Use a custom type
myRect = Rectangle 10 20
bigCircle = Circle 420000
describe : Shape -> String
describe shape =
case shape of
Point ->
"A lonely point"
Circle radius ->
"A circle of radius "
++ String.fromFloat radius
Rectangle width height ->
"A rectangle of area "
++ String.fromFloat (width*height)
Boolean
Defined by the language
-- Defined by Elm
type Bool = True | False
-- our code:
myBool = True
res =
case myBool of
True -> 42
False -> 18
Boolean
Defined by the language
-- Defined by Elm
type Bool = True | False
-- our code:
myBool = True
res =
case myBool of
True -> 42
False -> 18
res =
if myBool then
42
else
18
Preferred way:
if(condition) {
myVar = 42;
} else {
myVar = 18;
}
myVar = condition ? 42 : 18;
VS
Conditionals
in imperative language (Java, C, Python...)
Conditionals
in imperative language (Java, C, Python...)
myVar = condition ? 42 : 18;
VS
INSTRUCTION:
changes the state
EXPRESSION:
compute a new value
This is what Elm (and other FP languages does!)
if(condition) {
myVar = 42;
} else {
myVar = 18;
}
Implement highlight on hover
https://ellie-app.com/fF4BSNrDVK4a1
1st step: define Model & Msg and implement update
[] -- empty list
[1, 2, 6] : List number
["Hello", "world"] : List String
Lists
[] -- empty list
[1, 2, 6] : List number
["Hello", "world"] : List String
["Hello", 42] -- impossible!
Lists are homogeneous
ages : List Int
ages = [ 18, 14, 35, 10, 51 ]
agesInFiveYears : List Int
agesInFiveYears =
-- add five to each element
No for-loops!
addFive : Int -> Int
addFive x = 5 + x
ages : List Int
ages = [ 18, 14, 35, 10, 51 ]
agesInFiveYears : List Int
agesInFiveYears =
List.map addFive ages
No for-loops!
List.map :
(a -> b)
-> List a
-> List b
agesInFiveYears =
List.map addFive ages
Map signature
ages : List Int
ages = [ 18, 14, 35, 10, 51 ]
-- transform into :
-- [ "18 ans", "14 ans", ... ]
-- Hint:
-- String.fromInt : Int -> Str
Map challenge
ages : List Int
ages = [ 18, 14, 35, 10, 51 ]
displayAge : Int -> String
displayAge age =
String.fromInt age ++ " ans"
agesDisplayed =
List.map displayAge ages
Map challenge
{-| Compute the total number of chars in the
list of strings given in argument. Example:
totalLength ["hey!", "I am", "Hungry!!"]
returns 16
-}
totalLength : List String -> Int
totalLength strings = ...
-- HINT: List.sum : List Int -> Int
Map challenge 2
{-| Compute the total number of chars in the
list of strings given in argument. Example:
totalLength ["hey!", "I am", "Hungry!!"]
returns 16
-}
totalLength : List String -> Int
totalLength strings =
List.sum (List.map String.length strings)
Map challenge 2
Copy of Introduction to Functional Programming
By sebbes
Copy of Introduction to Functional Programming
- 657