-
Notifications
You must be signed in to change notification settings - Fork 0
/
Copy path02_functions.Rmd
87 lines (66 loc) · 2.95 KB
/
02_functions.Rmd
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
---
title: "Functions in R"
author: "Andreas Santucci"
output: html_document
---
# Functions as objects
We can inspect the source-code for many R functions by simply typing the name of the function. For example, suppose we want to see how R implements a linear model.
```{r, results='hold'}
head(lm)
tail(lm)
```
How can we interpret what is being displayed?
The function definition of `lm` is long, so we used `head` and `tail` to print out only the first few lines.
In this printout we see two components: the function *arguments* and the beginning of the function *body*.
* The function *arguments* of `lm` are named as `formula`, `data`, `subset`, `weights`, etc.
* The function *body* or definition begins after the `{` brace on line 4.
* The function *output* is the last expression in the body, just before the closing brace `}`.
It's interesting to note that the fact that we can even pass `lm` as an input argument to functions `head` and `tail` mean that *arguments to functions
may be functions themselves*.
# Defining Functions
We can define our own functions in R very easily.
```{r}
### Function: myFunction
# --------------------
# Input: theta, measured in radians from 0 to 2*pi.
# Output: A pair of points (x,y) representing the point on the unit circle
# intersected by ray emanating from the origin at angle theta.
myFunction <- function(theta) {
x <- cos(theta)
y <- sin(theta)
c(x, y)
}
```
We can immediately use our function.
```{r, results='hold'}
myFunction(0)
myFunction(pi/2)
myFunction(pi)
```
# Modes of Calling functions
We defined a named function above. Some functions may actually come in the form of *binary operators*. For example, the addition operator.
```{r,results='hold'}
1 + 10 # Infix notation.
`+`(1, 10) # Prefix notation.
```
Notice that we may either use infix or prefix notation to call the function `+` on the arguments `1` and `10`.
# Functions as arguments. A Toy Example
Realize that in R, many functions are already vectorized, such as `+`.
```{r}
1:10 + 21:30
```
However, what if we were to consider how one might implement the `sum` operator given a higher order function `Reduce`. Reduce takes as argument a *binary-function* `f` and an object `x`. The function is applied on the elements of the input object `x`, and the result returned.
```{r}
mySum <- function(x) Reduce(`+`, x)
myProd <- function(x) Reduce(`*`, x)
identical( mySum(1:10), sum(1:10))
all.equal(myProd(1:10), prod(1:10)) # Use all.equal to ignore type-difference.
```
# Next: `Apply` Functions
In the next section, we'll learn about `apply` functions, which themselves take in an object `X` with positive length and a function `FUN`; the function `FUN` is then applied to each element of object `X`.
# Practice problem: birthday countdown
Write a short R program which, given a birth-date, returns the number of days until said date. Check your answer with your neighbor.
```{r}
bdayCountdown <- function(date)
return(NULL)
```