When writing R Markdown documents and printing a table (e.g., an R data frame), it is handy to use a formatting function such as knitr::kable() so that the table looks nicely; otherwise the R Markdown output just mimics the R console. For example:

head(iris)
##   Sepal.Length Sepal.Width Petal.Length Petal.Width Species
## 1          5.1         3.5          1.4         0.2  setosa
## 2          4.9         3.0          1.4         0.2  setosa
## 3          4.7         3.2          1.3         0.2  setosa
## 4          4.6         3.1          1.5         0.2  setosa
## 5          5.0         3.6          1.4         0.2  setosa
## 6          5.4         3.9          1.7         0.4  setosa

Instead we want:

knitr::kable(head(iris))
Sepal.Length Sepal.Width Petal.Length Petal.Width Species
5.1 3.5 1.4 0.2 setosa
4.9 3.0 1.4 0.2 setosa
4.7 3.2 1.3 0.2 setosa
4.6 3.1 1.5 0.2 setosa
5.0 3.6 1.4 0.2 setosa
5.4 3.9 1.7 0.4 setosa

However, I don’t want to call kable() all the time – it just clutters my code and distracts from the important parts. Fortunately, it is possible to define kable() (or any other formatting function) as the default printing method for data frame (or matrices). This method is described in the knitr vignette Custom Print Methods. To this end, add the following code in an early chunk of your R Markdown document:

library(knitr) # it is necessary to load knitr
knit_print.data.frame = function(x, ...) {
    res = paste(c("", "", kable(x)), collapse = "\n")
    asis_output(res)
}
registerS3method("knit_print", "data.frame", knit_print.data.frame)

Now, if we output a data frame, we get the kable() output:

head(iris)
Sepal.Length Sepal.Width Petal.Length Petal.Width Species
5.1 3.5 1.4 0.2 setosa
4.9 3.0 1.4 0.2 setosa
4.7 3.2 1.3 0.2 setosa
4.6 3.1 1.5 0.2 setosa
5.0 3.6 1.4 0.2 setosa
5.4 3.9 1.7 0.4 setosa

I am not sure if there is an easier way available, but this works for me.

EDIT: There is indeed a much easier way by including the printing function in the YAML header (see here)

---
title: "Whatever"
output:
  html_document:
    df_print: kable
---

If we also want to print matrices using kable, we could adapt the procedure as follows:

knit_print.matrix = function(x, ...) {
    res = paste(c("", "", kable(x)), collapse = "\n")
    asis_output(res)
}
registerS3method("knit_print", "matrix", knit_print.matrix)

I am not sure yet if there is a better way to dispatch the printing function to both matrices and data frames at the same time.


Last updated: 2019-11-18

Back to the front page