]> git.donarmstrong.com Git - xtable.git/blob - pkg/vignettes/xtableGallery.Rnw
Vignette: no url package, no \R command, sort LaTeX pkgs, repaginate
[xtable.git] / pkg / vignettes / xtableGallery.Rnw
1 %\VignetteIndexEntry{xtable Gallery}\r
2 %\VignetteDepends{xtable}\r
3 %\VignetteKeywords{LaTeX, HTML, table}\r
4 %\VignettePackage{xtable}\r
5 % !Rnw weave = knitr\r
6 % \VignetteEngine{knitr::knitr}\r
7 %**************************************************************************\r
8 \documentclass{article}\r
9 \usepackage[a4paper,height=24cm]{geometry} % geometry first\r
10 \usepackage{array}\r
11 \usepackage{booktabs}\r
12 \usepackage{longtable}\r
13 \usepackage{parskip}\r
14 \usepackage{rotating}\r
15 \usepackage{tabularx}\r
16 \usepackage{titlesec}\r
17 \usepackage{hyperref} % hyperref last\r
18 \titleformat\subsubsection{\bfseries\itshape}{}{0pt}{}\r
19 \newcommand\p{\vspace{2ex}}\r
20 \newcommand\code[1]{\texttt{#1}}\r
21 \newcommand\pkg[1]{\textbf{#1}}\r
22 \setcounter{tocdepth}{2}\r
23 \begin{document}\r
24 \r
25 \title{The \pkg{xtable} Gallery}\r
26 \author{Jonathan Swinton and others}\r
27 \maketitle\r
28 \r
29 \tableofcontents\r
30 \r
31 \newpage\r
32 \r
33 \section{Introduction}\r
34 This document gives a gallery of tables which can be made using the\r
35 \pkg{xtable} package to create \LaTeX\ output. It doubles as a\r
36 regression check for the package.\r
37 \r
38 <<include=FALSE>>=\r
39 library(knitr)\r
40 opts_chunk$set(fig.path='figdir/fig', debug=TRUE, echo=TRUE)\r
41 @\r
42 \r
43 The first step is to load the package and set an option for this document.\r
44 <<results='asis'>>=\r
45 library(xtable)\r
46 options(xtable.floating = FALSE)\r
47 @\r
48 \r
49 \section{Gallery}\r
50 \subsection{Data frame}\r
51 <<results='asis'>>=\r
52 data(tli)\r
53 xtable(tli[1:10, ])\r
54 @\r
55 \r
56 \subsection{Matrix}\r
57 <<results='asis'>>=\r
58 design.matrix <- model.matrix(~ sex*grade, data = tli[1:10, ])\r
59 xtable(design.matrix, digits = 0)\r
60 @\r
61 \r
62 \newpage\r
63 \subsection{aov}\r
64 <<results='asis'>>=\r
65 fm1 <- aov(tlimth ~ sex + ethnicty + grade + disadvg, data = tli)\r
66 xtable(fm1)\r
67 @\r
68 \r
69 \subsection{lm}\r
70 <<results='asis'>>=\r
71 fm2 <- lm(tlimth ~ sex*ethnicty, data = tli)\r
72 xtable(fm2)\r
73 @\r
74 \r
75 \subsubsection{Anova table (one model)}\r
76 <<results='asis'>>=\r
77 xtable(anova(fm2))\r
78 @\r
79 \r
80 \subsubsection{Anova table (two models)}\r
81 <<results='asis'>>=\r
82 fm2b <- lm(tlimth ~ ethnicty, data = tli)\r
83 xtable(anova(fm2b, fm2))\r
84 @\r
85 \r
86 \newpage\r
87 \subsection{glm}\r
88 <<results='asis'>>=\r
89 fm3 <- glm(disadvg ~ ethnicty*grade, data = tli, family = binomial)\r
90 xtable(fm3)\r
91 @\r
92 \r
93 \subsubsection{Analysis of deviance}\r
94 <<results='asis'>>=\r
95 xtable(anova(fm3))\r
96 @\r
97 \r
98 \subsection{prcomp}\r
99 <<results='asis'>>=\r
100 pr1 <- prcomp(USArrests)\r
101 xtable(pr1)\r
102 @\r
103 \r
104 \p\r
105 <<results='asis'>>=\r
106 xtable(summary(pr1))\r
107 @\r
108 \r
109 <<include=FALSE>>=\r
110 # pr2 <- princomp(USArrests)\r
111 # xtable(pr2)\r
112 @\r
113 \r
114 \newpage\r
115 \r
116 \subsection{Time series}\r
117 <<results='asis'>>=\r
118 temp.ts <- ts(cumsum(1 + round(rnorm(100), 0)),\r
119               start = c(1954, 7), frequency = 12)\r
120 temp.table <- xtable(temp.ts, digits = 0)\r
121 temp.table\r
122 @\r
123 \r
124 \newpage\r
125 \r
126 <<include=FALSE>>=\r
127 # ## Demonstrate saving to file\r
128 # for(i in c("latex", "html")) {\r
129 #   outFileName <- paste("xtable.", ifelse(i=="latex", "tex", i), sep = "")\r
130 #   print(xtable(lm.D9), type = i, file = outFileName, append = TRUE,\r
131 #         latex.environments = NULL)\r
132 #   print(xtable(lm.D9), type = i, file = outFileName, append = TRUE,\r
133 #         latex.environments = "")\r
134 #   print(xtable(lm.D9), type = i, file = outFileName, append = TRUE,\r
135 #         latex.environments = "center")\r
136 #   print(xtable(anova(glm.D93, test = "Chisq")),\r
137 #         type = i, file = outFileName,\r
138 #         append = TRUE)\r
139 #   print(xtable(anova(glm.D93)), hline.after = c(1),\r
140 #         size = "small", type = i,\r
141 #         file = outFileName, append = TRUE)\r
142 #   # print(xtable(pr2), type = i, file = outFileName, append = TRUE)\r
143 # }\r
144 @\r
145 \r
146 \section{Helper functions for formatting}\r
147 The functions \code{xalign}, \code{xdigits}, and \code{xdisplay} are useful for\r
148 formatting tables in a sensible way. Consider the output produced by the default\r
149 formatting.\r
150 \r
151 <<results='asis'>>=\r
152 dat <- mtcars[1:3, 1:6]\r
153 x <- xtable(dat)\r
154 x\r
155 @\r
156 \r
157 \p\r
158 Now change the default alignment, digits and display using helper functions\r
159 \code{xalign}, \code{xdigits}, and \code{xdisplay}. This produces a better\r
160 format as shown below.\r
161 \r
162 <<results='asis'>>=\r
163 align(x) <- xalign(x)\r
164 digits(x) <- xdigits(x)\r
165 display(x) <- xdisplay(x)\r
166 x\r
167 @\r
168 \r
169 \newpage\r
170 \r
171 \section{Sanitization}\r
172 <<results='asis'>>=\r
173 insane <- data.frame(Name = c("Ampersand","Greater than","Less than",\r
174                             "Underscore","Per cent","Dollar",\r
175                             "Backslash","Hash","Caret","Tilde",\r
176                             "Left brace","Right brace"),\r
177                      Character = I(c("&",">","<","_","%","$",\r
178                                      "\\","#","^","~","{","}")))\r
179 colnames(insane)[2] <- paste(insane[, 2], collapse = "")\r
180 xtable(insane)\r
181 @\r
182 \r
183 \p\r
184 Sometimes you might want to have your own sanitization function.\r
185 \r
186 <<results='asis'>>=\r
187 wanttex <- xtable(data.frame(Column =\r
188                              paste("Value_is $10^{-",1:3,"}$", sep = "")))\r
189 print(wanttex, sanitize.text.function =\r
190       function(str) gsub("_", "\\_", str, fixed = TRUE))\r
191 @\r
192 \r
193 \newpage\r
194 \r
195 \subsection{Markup in tables}\r
196 Markup can be included in tables, including in column and row names, by using\r
197 a custom \code{sanitize.text.function}.\r
198 \r
199 <<results='asis'>>=\r
200 mat <- round(matrix(c(0.9, 0.89, 200, 0.045, 2.0), c(1, 5)), 4)\r
201 rownames(mat) <- "$y_{t-1}$"\r
202 colnames(mat) <- c("$R^2$", "$\\bar{x}$", "F-stat", "S.E.E", "DW")\r
203 mat <- xtable(mat)\r
204 print(mat, sanitize.text.function = function(x) {x})\r
205 @\r
206 \r
207 % By David Dahl to demonstrate contribution from David Whitting, 2007-10-09.\r
208 \p\r
209 You can also have sanitize functions that are specific to column or\r
210 row names.  In the table below, the row name is not sanitized but\r
211 column names and table elements are.\r
212 \r
213 <<results='asis'>>=\r
214 money <- matrix(c("$1,000","$900","$100"), ncol = 3,\r
215                 dimnames = list("$\\alpha$",\r
216                                 c("Income (US$)","Expenses (US$)",\r
217                                   "Profit (US$)")))\r
218 print(xtable(money), sanitize.rownames.function = function(x) {x})\r
219 @\r
220 \r
221 \section{Format examples}\r
222 \subsection{Adding a centering environment}\r
223 <<results='asis'>>=\r
224 print(xtable(anova(fm3), caption = "\\tt latex.environments = \"\""),\r
225       floating = TRUE, latex.environments = "")\r
226 print(xtable(anova(fm3), caption = "\\tt latex.environments = \"center\""),\r
227       floating = TRUE, latex.environments = "center")\r
228 @\r
229 \r
230 \newpage\r
231 \r
232 \subsection{Column alignment}\r
233 <<results='asis'>>=\r
234 tli.table <- xtable(tli[1:10, ])\r
235 align(tli.table) <- rep("r", 6)\r
236 tli.table\r
237 @\r
238 \r
239 \subsubsection{Left aligned strings with column lines}\r
240 <<results='asis'>>=\r
241 align(tli.table) <- "|rrl|l|lr|"\r
242 tli.table\r
243 @\r
244 \r
245 \subsubsection{Fixed width columns}\r
246 <<results='asis'>>=\r
247 align(tli.table) <- "|rr|lp{3cm}l|r|"\r
248 tli.table\r
249 @\r
250 \r
251 \newpage\r
252 \r
253 \subsection{Number of digits}\r
254 One number for all columns,\r
255 <<results='asis'>>=\r
256 display(tli.table)[c(2,6)] <- "f"\r
257 digits(tli.table) <- 3\r
258 tli.table\r
259 @\r
260 \r
261 \p\r
262 or one for each column, including the row names,\r
263 <<results='asis'>>=\r
264 digits(tli.table) <- 1:(ncol(tli)+1)\r
265 tli.table\r
266 @\r
267 \r
268 \p\r
269 or as a full matrix.\r
270 <<results='asis'>>=\r
271 digits(tli.table) <- matrix(0:4, nrow = 10, ncol = ncol(tli)+1)\r
272 tli.table\r
273 @\r
274 \r
275 \newpage\r
276 \r
277 \subsection{Suppress row/column names}\r
278 \subsubsection{Suppress row names}\r
279 <<results='asis'>>=\r
280 tli.table <- xtable(tli[1:10, ])\r
281 print(tli.table, include.rownames = FALSE)\r
282 @\r
283 \r
284 \p\r
285 If you want a vertical line on the left, you need to change the \code{align}\r
286 attribute.\r
287 <<results='asis'>>=\r
288 align(tli.table) <- "|r|r|lp{3cm}l|r|"\r
289 print(tli.table, include.rownames = FALSE)\r
290 @\r
291 \r
292 \p\r
293 Revert the alignment to what is was before.\r
294 <<>>=\r
295 align(tli.table) <- "|rr|lp{3cm}l|r|"\r
296 @\r
297 \r
298 \newpage\r
299 \r
300 \subsubsection{Suppress column names}\r
301 <<results='asis'>>=\r
302 print(tli.table, include.colnames = FALSE)\r
303 @\r
304 \r
305 \p\r
306 Note the doubled header lines which can be suppressed.\r
307 <<results='asis'>>=\r
308 print(tli.table, include.colnames = FALSE,\r
309       hline.after = c(0,nrow(tli.table)))\r
310 @\r
311 \r
312 \subsubsection{Suppress row and column names}\r
313 <<results='asis'>>=\r
314 print(tli.table, include.colnames = FALSE, include.rownames = FALSE)\r
315 @\r
316 \r
317 \newpage\r
318 \r
319 \subsection{Rotate row/column names}\r
320 The \code{rotate.rownames} and \code{rotate.colnames} arguments can be used to\r
321 rotate the row and/or column names. This requires \verb|\usepackage{rotating}|\r
322 in the \LaTeX\ preamble.\r
323 \r
324 <<results='asis'>>=\r
325 print(tli.table, rotate.rownames = TRUE, rotate.colnames = TRUE)\r
326 @\r
327 \r
328 \newpage\r
329 \r
330 \subsection{Horizontal lines}\r
331 \subsubsection{Line locations}\r
332 Use the \code{hline.after} argument to specify the position of the\r
333 horizontal lines.\r
334 \r
335 <<results='asis'>>=\r
336 print(xtable(anova(fm3)), hline.after = c(1))\r
337 @\r
338 \r
339 \subsubsection{Line styles}\r
340 Specifying \code{booktabs = TRUE} will generate three line types. By default,\r
341 when no value is given for \code{hline.after}, a \verb|\toprule| will be drawn\r
342 above the table, a \verb|\midrule| after the table headings and a\r
343 \verb|\bottomrule| below the table. This requires \verb|\usepackage{booktabs}|\r
344 in the \LaTeX\ preamble.\r
345 \r
346 \p\r
347 The top and bottom rules are slightly thicker than the mid rule. The thickness\r
348 of the lines can be set via the \LaTeX\ lengths \verb|\heavyrulewidth| and\r
349 \verb|\lightrulewidth|.\r
350 \r
351 <<results='asis'>>=\r
352 tli.table <- xtable(tli[1:10, ])\r
353 print(tli.table, include.rownames = FALSE, booktabs = TRUE)\r
354 @\r
355 \r
356 \p\r
357 If \code{hline.after} includes \code{-1}, a \verb|\toprule| will be\r
358 drawn above the table. If \code{hline.after} includes the number of\r
359 rows in the table, a \verb|\bottomrule| will be drawn below the\r
360 table. For any other values specified in \code{hline.after}, a\r
361 \verb|\midrule| will be drawn after that line of the table.\r
362 \r
363 \p\r
364 The following table has more than one \verb|\midrule|.\r
365 \r
366 <<results='asis'>>=\r
367 bktbs <- xtable(matrix(1:10, ncol = 2))\r
368 hlines <- c(-1, 0, 1, nrow(bktbs))\r
369 print(bktbs, booktabs = TRUE, hline.after = hlines)\r
370 @\r
371 \r
372 \subsection{Table level commands}\r
373 <<results='asis'>>=\r
374 print(xtable(anova(fm3)), size = "large")\r
375 @\r
376 \r
377 \p\r
378 <<results='asis'>>=\r
379 print(xtable(anova(fm3)), size = "\\setlength{\\tabcolsep}{12pt}")\r
380 @\r
381 \r
382 \subsection{Long tables}\r
383 Requires \verb|\usepackage{longtable}| in the \LaTeX\ preamble.\r
384 \r
385 <<results='asis'>>=\r
386 x <- matrix(rnorm(1000), ncol = 10)\r
387 x.big <- xtable(x, caption = "A \\code{longtable} spanning several pages")\r
388 print(x.big, hline.after=c(-1, 0), tabular.environment = "longtable")\r
389 @\r
390 \r
391 %% The column name alignment is off in the following example.\r
392 %% It needs some revision before exposing it. - CR, 7/2/2012\r
393 %\r
394 %% Tried to fix this and got some of the way, but \hlines are wrong\r
395 %% and first column is too wide. - DJS 4/10/2014\r
396 %% \subsubsection{Long tables with the header on each page}\r
397 %% The \code{add.to.row} argument can be used to display the header\r
398 %% for a long table on each page, and to add a "continued" footer\r
399 %% on all pages except the last page.\r
400 \r
401 %% \newcommand{\head}[1]{\centercell{\bfseries#1}}\r
402 \r
403 %% <<results='asis'>>=\r
404 %% x <- matrix(rnorm(1000), ncol = 10)\r
405 %% hdr <-  paste(paste("\\multicolumn{1}{c}{",1:9,"} & ", collapse = ""),\r
406 %%               "\\multicolumn{1}{c}{10}\\\\")\r
407 %% addtorow <- list()\r
408 %% addtorow$pos <- list()\r
409 %% addtorow$pos[[1]] <- c(0)\r
410 %% addtorow$command <- c(paste(\r
411 %%     hdr,\r
412 %%     "  \\hline \n",\r
413 %%     "  \\endhead \n",\r
414 %%     "  \\hline \n",\r
415 %%     "  {\\footnotesize Continued on next page} \n",\r
416 %%     "  \\endfoot \n",\r
417 %%     "  \\endlastfoot \n", sep = ""))\r
418 %% x.big2 <- xtable(x, label = "tabbig2", align = "lrrrrrrrrrr",\r
419 %%                  caption = "Example of longtable with the header on each page")\r
420 %% print(x.big2, tabular.environment = "longtable",\r
421 %%       include.rownames = FALSE, include.colnames = FALSE,\r
422 %%       add.to.row = addtorow)\r
423 %% @\r
424 \r
425 \newpage\r
426 \r
427 \subsection{Use of \code{add.to.row} argument}\r
428 The following frequency table has outer dimnames: \code{Grade3} and\r
429 \code{Grade6}.\r
430 \r
431 <<>>=\r
432 Grade3 <- c("A","B","B","A","B","C","C","D","A","B",\r
433             "C","C","C","D","B","B","D","C","C","D")\r
434 Grade6 <- c("A","A","A","B","B","B","B","B","C","C",\r
435             "A","C","C","C","D","D","D","D","D","D")\r
436 Cohort <- table(Grade3, Grade6)\r
437 Cohort\r
438 @\r
439 \r
440 \p\r
441 The default behavior of \code{print.xtable} is to strip outer dimnames.\r
442 <<results='asis'>>=\r
443 xtable(Cohort)\r
444 @\r
445 \r
446 \p\r
447 The desired column labels can be created using \code{add.to.row}, in this case\r
448 applying two commands to ``row number zero'' while suppressing the basic column\r
449 names.\r
450 \r
451 <<results='asis'>>=\r
452 addtorow <- list()\r
453 addtorow$pos <- list(0, 0)\r
454 addtorow$command <- c("& \\multicolumn{4}{c}{Grade 6} \\\\\n",\r
455                       "Grade 3 & A & B & C & D \\\\\n")\r
456 print(xtable(Cohort), add.to.row = addtorow, include.colnames = FALSE)\r
457 @\r
458 \r
459 \subsection{Sideways tables}\r
460 Requires \verb|\usepackage{rotating}| in the LaTeX\r
461 preamble.  Sideways tables can't be forced in place with the \code{[H]}\r
462 specifier, but you can use the \verb|\clearpage| command to get them\r
463 fairly nearby.\r
464 \r
465 <<results='asis'>>=\r
466 x <- x[1:30, ]\r
467 x.side <- xtable(x, caption = "A sideways table")\r
468 print(x.side, floating = TRUE, floating.environment = "sidewaystable")\r
469 @\r
470 \clearpage\r
471 \r
472 \subsection{Rescaled tables}\r
473 Specify a \code{scalebox} value to rescale the table.\r
474 <<results='asis'>>=\r
475 x <- x[1:20, ]\r
476 x.rescale <- xtable(x)\r
477 print(x.rescale, scalebox = 0.7)\r
478 @\r
479 \r
480 \subsection{Aligning fixed width columns}\r
481 Note that using specifications such as \verb|p{2cm}| always\r
482 produces a \textbf{left aligned} column. What if some other alignment\r
483 is desired?\r
484 \r
485 This is not really a problem with \pkg{xtable} but with the formatting\r
486 of tables with fixed width columns and different alignments using\r
487 standard \LaTeX.\r
488 \r
489 One solution is to use the \verb|array| package, defining new\r
490 column formats.\r
491 \r
492 \begin{verbatim}\r
493 \newcolumntype{L}[1]{>{\raggedright\let\newline\\\r
494     \arraybackslash\hspace{0pt}}m{#1}}\r
495 \newcolumntype{C}[1]{>{\centering\let\newline\\\r
496     \arraybackslash\hspace{0pt}}m{#1}}\r
497 \newcolumntype{R}[1]{>{\raggedleft\let\newline\\\r
498     \arraybackslash\hspace{0pt}}m{#1}}\r
499 \newcolumntype{P}[1]{>{\raggedright\tabularxbackslash}p{#1}}\r
500 \end{verbatim}\r
501 \r
502 These allow for very sophisticated cell formatting, namely\r
503 left-aligned, centred, or right-aligned text, with recognition of line\r
504 breaks for the first three new column types. If these lines are\r
505 included along with \verb|\usepackage{array}|, then the following\r
506 is possible.\r
507 \r
508 \newcolumntype{L}[1]{>{\raggedright\let\newline\\\r
509     \arraybackslash\hspace{0pt}}m{#1}}\r
510 \newcolumntype{C}[1]{>{\centering\let\newline\\\r
511     \arraybackslash\hspace{0pt}}m{#1}}\r
512 \newcolumntype{R}[1]{>{\raggedleft\let\newline\\\r
513     \arraybackslash\hspace{0pt}}m{#1}}\r
514 \newcolumntype{P}[1]{>{\raggedright\tabularxbackslash}p{#1}}\r
515 \r
516 <<results='asis'>>=\r
517 df <- data.frame(name = c("A","B"), right = c(1.4, 34.6),\r
518                  left = c(1.4, 34.6), text = c("txt1","txt2"))\r
519 print(xtable(df, align = c("l", "|c", "|R{3cm}", "|L{3cm}", "| p{3cm}|")),\r
520       floating = FALSE, include.rownames = FALSE)\r
521 @\r
522 \r
523 \newpage\r
524 \r
525 \subsection{Table width}\r
526 The \code{tabularx} environment is for typesetting tables whose overall width is\r
527 fixed. The column alignment code \code{X} denotes columns that will be stretched\r
528 to achieve the desired table width. Requires \verb|\usepackage{tabularx}| in the\r
529 \LaTeX\ preamble.\r
530 \r
531 <<results='asis'>>=\r
532 df.width <- data.frame(One = c("item 1", "A"), Two = c("item 2", "B"),\r
533                        Three = c("item 3", "C"), Four = c("item 4", "D"))\r
534 x.width <- xtable(df.width)\r
535 align(x.width) <- "|l|X|l|l|l|"\r
536 print(x.width, tabular.environment = "tabularx", width = "\\textwidth")\r
537 @\r
538 \r
539 \section{Suppressing printing}\r
540 By default the \code{print} method will print the \LaTeX\ or HTML to standard\r
541 output and also return the character strings invisibly.  The printing to\r
542 standard output can be suppressed by specifying \code{print.results = FALSE}.\r
543 \r
544 <<>>=\r
545 x.out <- print(tli.table, print.results = FALSE)\r
546 @\r
547 \r
548 Formatted output can also be captured without printing with the\r
549 \code{toLatex} method.  This function returns an object of class\r
550 \code{"Latex"}.\r
551 \r
552 <<>>=\r
553 x.ltx <- toLatex(tli.table)\r
554 class(x.ltx)\r
555 x.ltx\r
556 @\r
557 \r
558 \newpage\r
559 \r
560 \section{Acknowledgements}\r
561 Most of the examples in this gallery are taken from the \pkg{xtable}\r
562 documentation. Two examples (\code{add.to.row} and `Aligning fixed width\r
563 columns') are from Stack Exchange.\r
564 \r
565 \section{Session information}\r
566 <<results='asis'>>=\r
567 toLatex(sessionInfo())\r
568 @\r
569 \r
570 \end{document}\r