I am just starting to learn about KnitR and the use of Markdown in generating R documents and reports. This looks to be perfect for a lot of the day to day reporting that I have to do with my job. However, one thing that I'm not seeing is an easy way to print data frames and tables using Markdown formatting (sort of like xtable
, but with Markdown instead of LaTeX or HTML). I know that I can just embed the HTML output from xtable, but I was wondering if there were any Markdown-based solutions?

- 6,659
- 3
- 33
- 60
-
3Considering xtable and html.. Print html code with `print(xtable(data), type = "html")` . – user974514 Mar 18 '13 at 22:46
-
7@TARehman Your question reminded me that there was still no solution that produced tables directly compatible with `knitr`, so I sent a pull request to `pander` to add the table style. In future versions of `pander`, you should be able to do `pandoc.table(iris, style="rmarkdown")` – Marius Mar 20 '13 at 00:19
-
1@Marius Do you happen to know why pandoc isn't part of CRAN? Or when it might become part of it? Just curious. – TARehman Mar 22 '13 at 14:22
-
2@TARehman I'm not quite sure whether you meant pander or pandoc. `pander` should be up on CRAN. pandoc is a program written in Haskell that converts to and from a wide variety of different formats, it's not specific to R in any way. – Marius Mar 23 '13 at 03:04
-
@TARehman if you are on Windows, you could install `pandoc` easily with https://github.com/talgalili/installr. But @Marius is right, `pandoc` is not an R program, so will never land on CRAN of course. – daroczig Mar 24 '13 at 15:53
-
1Sorry, I meant `pander`, which wasn't on CRAN last time I had heard - not `pandoc`. My fault. :) – TARehman Mar 24 '13 at 19:40
-
Here's a html file that shows what half a dozen different methods produce: http://rpubs.com/benmarwick/tables_in_rmarkdown best pacakge for it is probably [hwriter](http://www.ebi.ac.uk/~gpau/hwriter/) – Ben May 12 '15 at 20:27
8 Answers
Now knitr
(since version 1.3) package include the kable
function for a creation tables:
> library(knitr)
> kable(head(iris[,1:3]), format = "markdown")
| Sepal.Length| Sepal.Width| Petal.Length|
|-------------:|------------:|-------------:|
| 5,1| 3,5| 1,4|
| 4,9| 3,0| 1,4|
| 4,7| 3,2| 1,3|
| 4,6| 3,1| 1,5|
| 5,0| 3,6| 1,4|
| 5,4| 3,9| 1,7|
UPDATED: if you get raw markdown in a document try setup results = "asis"
chunk option.

- 9,193
- 6
- 52
- 57
-
26when running inside knitr, you can leave out the `format` argument, since knitr is aware of the output format and will automatically set it – Yihui Xie Nov 12 '13 at 06:20
-
3
-
I have the sample problem, I just get raw markdown, not formatted table. – the_skua May 19 '14 at 14:27
-
7
-
6
Two packages that will do this are pander
library(devtools)
install_github('pander', 'Rapporter')
Or ascii
pander
is a slightly different approach to report construction, (but can be useful for this feature).
ascii
will allow you to print
with type = 'pandoc
(or various other markdown flavours)
library(ascii)
print(ascii(head(iris[,1:3])), type = 'pandoc')
**Sepal.Length** **Sepal.Width** **Petal.Length**
--- ------------------ ----------------- ------------------
1 5.10 3.50 1.40
2 4.90 3.00 1.40
3 4.70 3.20 1.30
4 4.60 3.10 1.50
5 5.00 3.60 1.40
6 5.40 3.90 1.70
--- ------------------ ----------------- ------------------
Note that in both these cases, it is directed towards using pandoc
to convert from markdown to your desired document type, however using style='rmarkdown'
will create tables that are compatible with this markdown
package and inbuilt conversion in rstudio
.

- 113,303
- 27
- 265
- 254
-
3Just a note about `pander`: it can produce the `rmarkdown` styled tables also beside others, e.g.: `pander(head(iris[,1:3]), style = 'rmarkdown')` – daroczig Nov 09 '13 at 21:23
-
Just wanted to update this with what I settled on doing. I am using the hwriter
package right now to print out tables, and using the row.*
and col.*
features to put CSS classes on to different elements. Then, I wrote custom CSS to make my display as I wanted it. So, here's an example in case anyone else is dealing with something similar.
First, create a file that will do the knitting
and change the Markdown into HTML:
FILE: file_knit.r
#!/usr/bin/env Rscript
library(knitr)
library(markdown)
knit("file.Rmd")
markdownToHTML("file.md","file.html",stylesheet="~/custom.css")
Next, create the actual Markdown file:
FILE: file.Rmd
Report of Fruit vs. Animal Choices
==================================
This is a report of fruit vs. animal choices.
```{r echo=FALSE,results='asis'}
library(hwriter)
set.seed(9850104)
my.df <- data.frame(Var1=sample(x=c("Apple","Orange","Banana"),size=40,replace=TRUE),
Var2=sample(x=c("Dog","Cat","Bunny"),size=40,replace=TRUE))
tbl1 <- table(my.df$Var1,my.df$Var2)
tbl1 <- cbind(tbl1,rowSums(tbl1))
tbl1 <- rbind(tbl1,colSums(tbl1))
colnames(tbl1)[4] <- "TOTAL"
rownames(tbl1)[4] <- "TOTAL"
# Because I used results='asis' for this chunk, I can just use cat() and hwrite() to
# write out the table in HTML. Using hwrite()'s row.* function, I can assign classes
# to the various table elements.
cat(hwrite(tbl1,
border=NA,
table.class="t1",
row.class=list(c("header col_first","header col","header col","header col", "header col_last"),
c("col_first","col","col","col","col_last"),
c("col_first","col","col","col","col_last"),
c("col_first","col","col","col","col_last"),
c("footer col_first","footer col","footer col","footer col","footer col_last"))))
```
Finally, just create a custom CSS file.
FILE: custom.css
body {
font-family: sans-serif;
background-color: white;
font-size: 12px;
margin: 20px;
}
h1 {font-size:1.5em;}
table {
border: solid;
border-color: black;
border-width: 2px;
border-collapse: collapse;
margin-bottom: 20px;
text-align: center;
padding: 0px;
}
.t1 .header {
color: white;
background-color: black;
border-bottom: solid;
border-color: black;
border-width: 2px;
font-weight: bold;
}
.t1 .footer {
border-top: solid;
border-color: black;
border-width: 2px;
}
.t1 .col_first {
border-right: solid;
border-color: black;
border-width: 2px;
text-align: left;
font-weight: bold;
width: 75px;
}
.t1 .col {
width: 50px;
}
.t1 .col_last {
width: 50px;
border-left: solid;
border-color: black;
border-width: 2px;
}
Executing ./file_knit.r
gives me file.html, which looks like this:
So, hopefully this might be helpful to others who want a bit more formatting in Markdown output!

- 6,659
- 3
- 33
- 60
-
1Yes, nope. Will work with Markdown-->HTML but not with Markdown-->PDF, Markdown-->DOCX ... The question is about using Markdown in general not only for the purpose of creating HTML files with it -- might have been your intention, but is not written down there. – petermeissner Sep 18 '14 at 16:17
-
Did you notice I'm answering my own question? I can edit the question or tag it differently if you think it would help? – TARehman Sep 18 '14 at 17:47
-
Incidentally, at the time of this answer, knitr was only supporting HTML. That's why the question doesn't explicitly say anything about HTML. – TARehman Sep 18 '14 at 17:55
-
jip, changing the question would help ... but why making it more specific when it is of more use for all when it is broader and more general? In regard to you answering your own question, well the others provide tables in Markdown format you provide tables in HTML format - its not wrong but I find the other answers simply down to the point, elegant and more helpful. not everybody has to like your answer, does it not suffice that did like your answer? – petermeissner Sep 19 '14 at 05:18
-
7You yourself have said that my answer is not wrong, but that others are better. The correct application of the voting system is to upvote the better answers, not to downvote mine. See also here: http://stackoverflow.com/help/privileges/vote-down "Use your downvotes whenever you encounter an egregiously sloppy, no-effort-expended post, or an answer that is clearly and perhaps dangerously incorrect." – TARehman Sep 19 '14 at 16:00
-
where we have to place the css file which we included in r markdown file – Moby M Aug 02 '17 at 07:38
-
You can specify the path to the CSS file in the markdownToHTML() function. – TARehman Aug 02 '17 at 12:04
There are functions in the pander
package:
> library(pander)
> pandoc.table(head(iris)[, 1:3])
-------------------------------------------
Sepal.Length Sepal.Width Petal.Length
-------------- ------------- --------------
5.1 3.5 1.4
4.9 3 1.4
4.7 3.2 1.3
4.6 3.1 1.5
5 3.6 1.4
5.4 3.9 1.7
-------------------------------------------

- 58,213
- 16
- 107
- 105
-
4Thanks for promoting `pander` :) Please note that you might also use the generic S3 method to save a few chars to type, like: `pander(head(iris)[, 1:3])` – daroczig Mar 19 '13 at 09:23
It is not very hard to make your own customized function. Here is a very simple proof of concept to generate an rmarkdown table of a data.frame
:
rmarkdownTable <- function(df){
cat(paste(names(df), collapse = "|"))
cat("\n")
cat(paste(rep("-", ncol(df)), collapse = "|"))
cat("\n")
for(i in 1:nrow(df)){
cat(paste(df[i,], collapse = "|"))
cat("\n")
}
invisible(NULL)
}
In .Rmd document you would then use the function with results = 'asis'
:
```{r, results = 'asis'}
rmarkdownTable <- function(df){
cat(paste(names(df), collapse = "|"))
cat("\n")
cat(paste(rep("-", ncol(df)), collapse = "|"))
cat("\n")
for(i in 1:nrow(df)){
cat(paste(df[i,], collapse = "|"))
cat("\n")
}
invisible(NULL)
}
rmarkdownTable(head(iris))
```
The code above would give you the following figure (in the example this is the pdf output, but since the table is in markdwon, you could knit into html or word too).
From here - and reading other people´s code - you can figure out how to manipulate the text to generate the table you want and create more personalized functions.

- 11,354
- 9
- 43
- 66
-
1this is great, but do you know how to make this align on the left side instead of centered? – Patrick Aug 20 '15 at 04:07
use a combination of knitr::kable and xtable in your markdown document.
library("knitr","xtable")
for a simple data.frame -
kable(head(mtcars[,1:4]),format="markdown")
kable(head(mtcars[,1:4]),format="pandoc",caption="Title of the table")
format="pandoc"
allows more options like caption.
Now the combination for model summary.
data(tli)
fm1 <- aov(tlimth ~ sex + ethnicty + grade + disadvg, data=tli)
kable(xtable(fm1), caption = "Annova table")
for even more options look at stargazer
package instead of xtable
.

- 1,090
- 12
- 9
To write / create Markdown tables in R, you can also use MarkdownReports' MarkDown_Table_writer_DF_RowColNames()
or MarkDown_Table_writer_NamedVector()
functions. You just pass on a data frame / matrix with dimension names, or a vector with names, and it parses & writes out the table in Markdown format.

- 689
- 7
- 16
My function for Gitlab:
to_markdown<-function(df) {
wrap<-function(x,sep=" ") paste0("|", sep, paste(x, collapse=paste0(sep,"|",sep)), sep, "|", sep=sep)
paste0(wrap(colnames(df)),
"\n",
wrap(rep("------", ncol(df)),sep=""),
"\n",
paste(apply(df, 1, wrap), collapse="\n"))
}
cat(to_markdown(head(iris[,1:3])))
| Sepal.Length | Sepal.Width | Petal.Length |
|------|------|------|
| 5.1 | 3.5 | 1.4 |
| 4.9 | 3 | 1.4 |
| 4.7 | 3.2 | 1.3 |
| 4.6 | 3.1 | 1.5 |
| 5 | 3.6 | 1.4 |
| 5.4 | 3.9 | 1.7 |

- 2,014
- 20
- 24