Arrow: is right associative
Function Application: is left associative
higher order function (take in function): takes in function as argument

val plus = fn (x : int) => fun (y : int) => x + y

Currying (returning a function): take argument in function (instead of tuples)
Partial application: you do not have to finish applying tuples when you do currying.
Function composition (lower case o): compose function before applying

fun compose (f, g): (('b -> 'c) * ('a -> 'b) -> 'a -> 'c) = fn x => f (g x)
fun compose (f, g) x = f (g x)
fun plus x y = x+y

Filter as Example

fun filter (_: 'a -> bool) ([] : 'a list) : 'a list = []
| filter f (x::xs) = if f x then x :: filter f xs else filter f xs
filter (fn n => n mod 2 = 0) [1, 2, 3, 4, 5] |-> [2, 4]

Fold

foldl: ('a * 'b -> 'b) -> 'b -> 'a list -> 'b
foldr: ('a * 'b -> 'b) -> 'b -> 'a list -> 'b
foldl f b [x1,...,xn] ~= f(xn f(x2, f (x1, b)))
foldr f b [x1,...,xn] ~= f(x1 f(x_{n-1}, f (x_n, b)))
fun foldl f b [] = b
| foldl f b (x::xs) = foldl f (f(x, b)) xs
(*This is trail recursive*)
fun foldr f b [] = b
| foldr f b (x::xs) = f (x, folder f b xs)
(*This is not trail recursive*)

If we see partially applied function as one function: