Zhuoran (John) Li
A programming paradigm mapped from mathematical functions
Declarative
(what)
Imperative
(how)
vs
🥳
Given the same input, will always return the same output and produces no side effects
// Pure const add = (a, b) => a + b add(1, 2) // 3 add(1, 2) // 3 [1, 2, 3].slice(0, 1) // [1] // Impure let a = 1; const increment = n => a += n increment(1) // 2 increment(1) // 3 [1, 2, 3].splice(0, 1) // [1] Math.random() // 0.8227538687335922 Math.random() // 0.6780092463695311
// Pure const add = (a, b) => a + b add(1, 2) // 3 add(1, 2) // 3 [1, 2, 3].slice(0, 1) // [1] // Impure let a = 1; const increment = n => a += n increment(1) // 2 increment(1) // 3 [1, 2, 3].splice(0, 1) // [1] Math.random() // 0.8227538687335922 Math.random() // 0.6780092463695311
// Pure const add = (a, b) => a + b add(1, 2) // 3 add(1, 2) // 3 [1, 2, 3].slice(0, 1) // [1] // Impure let a = 1; const increment = n => a += n increment(1) // 2 increment(1) // 3 [1, 2, 3].splice(0, 1) // [1] Math.random() // 0.8227538687335922 Math.random() // 0.6780092463695311
// Pure const add = (a, b) => a + b add(1, 2) // 3 add(1, 2) // 3 [1, 2, 3].slice(0, 1) // [1] // Impure let a = 1; const increment = n => a += n increment(1) // 2 increment(1) // 3 [1, 2, 3].splice(0, 1) // [1] Math.random() // 0.8227538687335922 Math.random() // 0.6780092463695311
Using side effects is NOT forbidden!
Transforms a function with multiple arguments into a sequence/series of functions each taking a single argument.
const add = a => b => a + b const increment = add(1) const increment(2) // 3 === add(1)(2)
const water = cond([ [equals(0), always('water freezes at 0°C')], [equals(100), always('water boils at 100°C')], [T, temp => `nothing special happens at ${temp}°C`] ]) const isEligibleToVote = both(isOverEighteen, isCitizen)
const water = temperature => cond([ [val => equals(0, val), val => always('water freezes at 0°C')], [val => equals(100, val), val => always('water boils at 100°C')], [T, temp => `nothing special happens at ${temp}°C`] ])(temperature) const isEligibleToVote = age => both( val => isOverEighteen(val), val => isCitizen(val) )(age)
const water = temperature => cond([ [val => equals(0, val), val => always('water freezes at 0°C')], [val => equals(100, val), val => always('water boils at 100°C')], [T, temp => `nothing special happens at ${temp}°C`] ])(temperature) const isEligibleToVote = age => both( val => isOverEighteen(val), val => isCitizen(val) )(age)
🥳 After
🤪 Before
h(g(f(x)))
compose(h, g, f)(x)
const toAlladin = compose(g, f) toAlladin(aPerson)
const toAlladin = pipe(f, g) toAlladin(aPerson)
compose: right -> left
pipe: left -> right
Identity and Associativity
// Identity [2].map(x => x) === [2] // Associativity const f = x => x * 2 const g = x => x + 2 [2].map(g).map(f) === [2].map(compose(f, g)) // [8] [8]
Initial
(Not Asked)
Verifying One-time URL
(Loading)
Invalid URL
(Failure)
Valid URL
(Success)
Remote Object - Tagged Union (Sum Types)
Verifying One-time URL
Error (e.g. Invalid Reset Password URL)
Initial State
Success
Productivity plugin in Alfred
The End