# Higher-order function

File:Higherorderfunctions.jpg
A simple diagram of a Higher order function. It either takes in a function, returns a function, or does both.

A higher-order function (HOF) is a function that is specialized by another function or that produces another function (i.e. it accepts a function as an argument and/or returns a function).

## Background

Functions are data, so we can treat them like all other objects (e.g. numbers, strings, booleans, etc.) and use them as arguments or return values.

HOFs allow us to build abstractions by passing actions (functions) around. For example, a recurring pattern is applying a specific function to all the elements of a list. `map` abstracts away the details of this behavior, allowing us to apply any function that is passed in.

## Examples

### Functions as arguments

```def map(f, iterable):
return (f(x) for x in iterable)```
```def filter(f, iterable):
return (x for x in iterable if f(x))```
```def iter_solve(guess, done, update):
while not done(guess):
guess = update(guess)
return guess```

### Functions as return values

```def make_adder(n):
return x + n
```def countdown(n):
def tick():
nonlocal n
n -= 1
return n
return tick```
```def rational(x, y):
def dispatch(field):
if field == 'numer':
return x
elif field == 'denom':
return y
else:
return 'invalid field'
return dispatch```

### Both

```def make_doubler(f):
def doubler(*args)
f(f(*args))
return doubler```
`curry = lambda f: lambda x: lambda y: f(x, y)`