5

I have a really wide table (300+ columns) and would like to display it by wrapping the columns. In the example I will just use 100 columns.

What I have in mind is repetitively using kable to display the subset of the table:

library(kableExtra)
set.seed(1)
data = data.frame(matrix(rnorm(300, 10, 1), ncol = 100))

kable(data[, 1:5], 'latex', booktabs = T) 
kable(data[, 6:10], 'latex', booktabs = T) 
kable(data[, 11:15], 'latex', booktabs = T) 

But this is apparently tedious... I know there are scaling down options but since I have so many columns, it won't be possible.

Is there any parameter I can twist in kable to make it happen?


Updated: @jay.sf 's answer seems working well, but it didn't yield the same result here. Instead I got some plain code - could you please have a second look and let me know where can I improve? Thanks!

results

my sessionInfo() is: R version 3.5.1 (2018-07-02) with rmarkdown::pandoc_version() of 1.19.2.1.

Rachel Zhang
  • 562
  • 6
  • 20
  • To get pure LaTeX code we have to use `cat`, `sapply` gave a funny output we therefore apply a `for` loop, see my edits, should work fine now. – jay.sf Mar 17 '19 at 16:18

2 Answers2

2

You could use a matrix containing your columns numbers and give it into a for loop with the cat function inside.

---
output: pdf_document
---

```{r, results="asis", echo=FALSE}
library(kableExtra)
set.seed(1)
dat <- data.frame(matrix(rnorm(300, 10, 1), ncol=100))

m <- matrix(1:ncol(dat), 5)

for (i in 1:ncol(m)) {
 cat(kable(dat[, m[, i]], 'latex', booktabs=TRUE), "\\newline")
}
```

Result

enter image description here

jay.sf
  • 60,139
  • 8
  • 53
  • 110
  • Hi jay, thank you for your response. It is weird that I copied and pasted your code but didn't yield the same results in my pdf file. It did not displayed in the form of kable tables but basically plain codes. I updated the screenshot in my question description. – Rachel Zhang Mar 18 '19 at 01:37
  • Weird, @RachelZhang, this is exactly what happens to me when I don't have specified option `results="asis"` of the chunk in which I run the code ([Ref.](https://www.rstudio.com/wp-content/uploads/2016/03/rmarkdown-cheatsheet-2.0.pdf)), could you check that? Otherwise, could you post your `sessionInfo()`, your `rmarkdown::pandoc_version()`, and which LaTeX distribution & version you have installed? – jay.sf Mar 18 '19 at 06:36
2

This question is actually trickier than I thought at first glance. I used some tidyverse functions, specifically dplyr::select to get columns and purrr::map to move along groups of column indices.

My thinking with this was to make a list of vectors of column indices to choose, such that the first list item is 1:20, the second is 21:40, and so on, in order to break the data into 20 tables of 5 columns each (the number you use can be a different factor of ncol(data)). I underestimated the work to do that, but got ideas from an old SO post to rep the numbers 1 to 20 along the number of columns, sort it, and use that as the grouping then to split the columns.

Then each of those vectors becomes the column indices in select. The resulting list of data frames each gets passed to knitr::kable and kableExtra::kable_styling. Leaving things off there would get map's default of printing names as well, which isn't ideal, so I added a call to purrr::walk to print them neatly.

Note also that making the kable'd tables this way meant putting results="asis" in the chunk options.

---
title: "knitr chunked"
output: pdf_document
---

```{r include=FALSE}
library(knitr)
library(kableExtra)
library(dplyr)
library(purrr)

set.seed(1)
data = data.frame(matrix(rnorm(300, 10, 1), ncol = 100))
```

```{r results='asis'}
split(1:ncol(data), sort(rep_len(1:20, ncol(data)))) %>%
  map(~select(data, .)) %>%
  map(kable, booktabs = T) %>%
  map(kable_styling) %>%
  walk(print)
```

Top of the PDF output:

pdf

camille
  • 16,432
  • 18
  • 38
  • 60
  • Just want to note that I'd originally broken this into 15 tables of 7 columns just because that was a size where the tables fit fairly neatly in the PDF pages, but decided to change to 20 tables of 5 columns each to better fit what you'd described. Both code and output are updated to match that. – camille Mar 17 '19 at 18:19