14.1 Reuse code chunks
You can freely reuse code chunks anywhere in your source document without cut-and-paste. The key is to label your code chunks, so you can refer to them with labels in other places. There are three ways to reuse code chunks.
14.1.1 Embed one chunk in another chunk (*)
You can embed one code chunk in another code chunk by enclosing its label in <<>>
. Then knitr will automatically expand the string <<label>>
to the actual code. For example, you can create an R function in this way:
We define a function to convert Fahrenheit to Celsius.
```{r, f2c}
F2C <- function(x) {
<<check-arg>>
<<convert>>
}
```
First, we check if the input value is numeric:
```{r, check-arg, eval=FALSE}
if (!is.numeric(x)) stop("The input must be numeric!")
```
Then we do the actual conversion:
```{r, convert, eval=FALSE}
(x - 32) * 5/ 9
```
This is based on one of the main ideas of Literate Programming, which was proposed by Donald Knuth. The advantage of this technique is that you can split (complex) code into smaller parts, write each part in a separate code chunk, and explain them with narratives. All parts can be composed into the main code chunk to be executed.
For the above example, the first code chunk (with the label f2c
) will become:
```{r, f2c}
F2C <- function(x) {
if (!is.numeric(x)) stop("The input must be numeric!")
(x - 32) * 5/ 9
}
```
You can embed an arbitrary number of other code chunks in one code chunk. The embedding can also be recursive. For example, you may embed chunk A in chunk B, and chunk B in chunk C. Then chunk C will include code from chunk A via chunk B.
The marker <<label>>
does not have to be on a separate line. It can be embedded anywhere in a code chunk.
14.1.2 Use the same chunk label in another chunk
If you want to use exactly the same code chunk two or more times, you may define the chunk with a label, and create more code chunks with the same label but leave the chunk content empty, e.g.,
Here is a code chunk that is not evaluated:
```{r, chunk-one, eval=FALSE}
1 + 1
2 + 2
```
Now we actually evaluate it:
```{r, chunk-one, eval=TRUE}
```
We used the chunk label “chunk-one” twice in the above example, and the second chunk just reuses code from the first chunk.
We recommend that you do not use this method to run a code chunk more than once to generate plots (or other files), because plot files created from a later chunk may overwrite files from a previous chunk. It is okay if only one of such chunks uses the chunk option eval = TRUE
, and all other chunks use eval = FALSE
.
14.1.3 Use reference labels (*)
The chunk option ref.label
takes a vector of chunk labels to retrieve the content of these chunks. For example, the code chunk with the label chunk-a
is the combination of chunk-c
and chunk-b
below:
```{r chunk-a, ref.label=c('chunk-c', 'chunk-b')}
```
```{r chunk-b}
# this is the chunk b
1 + 1
```
```{r chunk-c}
# this is the chunk c
2 + 2
```
In other words, chunk-a
is essentially this:
```{r chunk-a}
# this is the chunk c
2 + 2
# this is the chunk b
1 + 1
```
The chunk option ref.label
has provided a very flexible way of reorganizing code chunks in a document without resorting to cut-and-paste. It does not matter if the code chunks referenced are before or after the code chunk that uses ref.label
. An early code chunk can reference a later chunk.
There is an application of this chunk option in Section 4.19.