Making tables with RStudio and LaTeX

The following uses two approaches to make tables in LaTeX. The issue I’ve seen with many solutions is that the examples provided are “toy” examples without the kinds of requirements of real papers (e.g., notes explaining the contents of tables, multiple panels in a given table). The code below constitutes a .Rnw document that should compile with RStudio and the knitr package.
Note that it requires a few other R packages, including plyr, sandwich, lmtest, xtable, and texreg.

The code is based on an example used by Mitchell Petersen to illustrate two-way cluster-robust standard errors (see here). See here for the compiled PDF.

\documentclass{article}

\usepackage{pdflscape}
\usepackage{array}
\usepackage{booktabs}
\usepackage{dcolumn}
\usepackage{palatino}

\begin{document}
<<get_data, message=FALSE, echo=FALSE, results='hide'>>=
# Tests of R function using Mitchell Petersen's test-data

# Read the data
test <- read.table(
      url(paste("http://www.kellogg.northwestern.edu/",
            "faculty/petersen/htm/papers/se/",
            "test_data.txt",sep="")),
    col.names=c("firmid", "year", "x", "y"))
source("http://www.people.hbs.edu/igow/GOT/Code/cluster2.R")

# The fitted model
fm <-    lm(y ~ x, data=test)

# Tests
library(sandwich); library(lmtest)
se.ols   <- coeftest(fm)                                  # OLS
se.white <- coeftest(fm, vcov=vcovHC(fm, type="HC0"))     # White
se.i     <- coeftest.cluster(test,fm, cluster1="firmid")  # Clustered by firm
se.t     <- coeftest.cluster(test,fm, cluster1="year")    # Clustered by year
se.it    <- coeftest.cluster(test,fm, cluster1="firmid",
                             cluster2="year")             # Clustered by firm and year
@

<<table_funcs, cache=TRUE, echo = FALSE, results='hide', message=FALSE>>=
print_table <- function(table, caption=NULL, note="", number=TRUE) {
  if (is.null(caption)) {
    caption <- ""
    sub.str <- ""
  } else {
    sub.str <- "\\1"
  }
  the.table <- xtable(table, caption=caption)
  temp <- toLatex(the.table, include.rownames=FALSE, caption.placement="top")
  replacement <- paste(" \\\\begin{tabular}{l}",
                       "\\\\begin{minipage}[t]{\\\\columnwidth}",
                       sub.str,  "{\\\\small ",
                       note, "\\\\newline } \\\\end{minipage} ",
                       " \\\\end{tabular} ", sep=" ")
  temp <- gsub("(\\\\caption\\{[^}]*?\\})", replacement, temp)
  if (!number & sub.str!="") {
    temp <- gsub("\\\\begin\\{table\\}",
                 "{\\\\addtocounter{table}{-1}} \\\\begin{table}", temp)
  }
  print(temp)
}
@

<<using_xtable, message=FALSE, eval=TRUE, echo=FALSE, results='asis'>>=
require(xtable)
require(plyr)

# Panel A
panel.a <- as.data.frame(table(test$year))
names(panel.a) <- c("Year", "N")
note <- paste("\\\\textbf{Panel A.} Number of observations by year.",
              "This table uses a function that calls the xtable package.")
xpanel.a <- xtable(panel.a)
print_table(xpanel.a, caption="Descriptive statistics", note=note)

# Panel B
panel.b <- ddply(test, .(year), summarize,
                 p25= quantile(y, probs=.25),
                 p50= quantile(y, probs=.25),
                 p75= quantile(y, probs=.25),
                 mean= mean(y))
note <- paste("\\\\textbf{Panel B.} Here are some summary statistics by year.")
xpanel.b <- xtable(panel.b)
print_table(xpanel.b, note=note) # no caption means that this will (look to)
                                 # be part of the same table as the previous one.
@

\begin{table}
\caption{Regression table}
\begin{tabular}[t]{c}
\begin{minipage}[t]{\columnwidth}
{\footnotesize
This table uses the texreg package. But in a way that allows placement of a note above the table.
\newline}
\end{minipage} \tabularnewline
<<tabulate_results, message=FALSE, echo=FALSE, results='asis'>>=
# Tabulate results
library(texreg)
texreg(list(fm, fm, fm, fm, fm),
      table = FALSE,
      stars = c(0.01, 0.05, 0.1),
      booktabs=TRUE, use.packages = FALSE, dcolumn=TRUE,
      custom.model.names = c("OLS", "White", "Cl-i", "Cl-t", "Cl-2"),
      override.se=  list(se.ols[,2], se.white[,2], se.i[,2], se.t[,2], se.it[,2]),
      override.pval=list(se.ols[,4], se.white[,4], se.i[,4], se.t[,4], se.it[,4]))
@
\end{tabular}
\label{reg-table}
\end{table}

\end{document}
Advertisements
This entry was posted in Uncategorized. Bookmark the permalink.

Leave a Reply

Fill in your details below or click an icon to log in:

WordPress.com Logo

You are commenting using your WordPress.com account. Log Out / Change )

Twitter picture

You are commenting using your Twitter account. Log Out / Change )

Facebook photo

You are commenting using your Facebook account. Log Out / Change )

Google+ photo

You are commenting using your Google+ account. Log Out / Change )

Connecting to %s