Putting line number for R code with knitr

4.1k views Asked by At

I wonder if there is any function to put line numbers with knitr in .Rnw. I found this discussion and some documents (now removed from the web) but could not find the way to put line numbers.

3

There are 3 answers

4
Thomas On BEST ANSWER

This solution uses the LaTeX listings package to create line numbers. I can only get them to work by accumulating across all code chunks, but I imagine there is a similar solution that will enumerate lines only within each chunk. Here's the .Rnw source:

\documentclass{article}
\usepackage{listings}
\begin{document}

<<setup, echo=FALSE>>=
knit_hooks$set(source = function(x, options) {
    paste("\\begin{lstlisting}[numbers=left, firstnumber=last]\n", x, 
        "\\end{lstlisting}\n", sep = "")
})
@

<<a, results='hold'>>=
1:2
3:4
5:6
@

<<b>>=
"test1"
"test2"
"test3"
@

\end{document}

The key parts of this are in the source hook, which is basically copied from here. The firstnumber=last tells listings to accumulate line numbers across listings. Without it, all lines are numbered 1 because knitr is putting each code line in its own listing.

And here's the result:

enter image description here

If you want each code block to start numbering from 1, add a hook to reset the counter:

knit_hooks$set(reset = function(before, options, envir){
if(before){
    return("\\setcounter{lstnumber}{1}")
}
})

and then use reset=TRUE to activate the hook in each chunk you want:

<<a, results='hold', reset=TRUE>>=
1:2
3:4
@
1
LukasKawerau On

For use in HTML, you can set the chunk option class.source to pass custom css to the output:

```{r class.source = c("numCode", "R", "numberLines")}
# your code
```
0
StatsStudent On

When using knitr with Lyx or Latex, I've found it helpful to add the lineno package to the document pre-amble and then to enclose the chunk with the \internallinenumbers \resetlinenumber[13].

Here's a minimal example:

\usepackage{lineno}

then in the body text, add the following before the code chunk:

{\internallinenumbers \resetlinenumber[13]

and then this after the code chunk:

}

With LyX (what I use for rapid LaTeX generation), I simply go to the document menu, then Settings->LaTeX Preamble and I add \usepackage{lineno}, click Apply, OK, and then Close. Then in the main document before my code chunk, I insert LaTeX source by clicking the "TEX" button menu button or by pressing "Ctrl+L" on the keyboard. Then I paste in {\internallinenumbers \resetlinenumber[13]. Finally, I place the cursor immediately after the code chunk and do the same thing. only I close the line numbering with a curly brace: }.

Here is a minimal example, when the code is in place is pasted below:

\documentclass[english]{article}
\usepackage{lineno}
\begin{document}
First line in main document before code chunk.

{\internallinenumbers \resetlinenumber[13]

<<CodeBlock1, highlight=TRUE, eval=FALSE, size="small">>=
x<-rnorm(10)
mean(x)
@
}
\end{document}