Search code examples
rsweavextable

xtable output for a list of tables


I've a list of tables and want to sweave it for LaTex output. Here is the code:

Data <- esoph[ , 1:3]
library(plyr)
combos <- combn(ncol(Data),2)

TabelFn <- function(x) {
  Table <- addmargins(table(Data[, x[1]], Data[, x[2]]))
  return(Table)
  }

Table <- alply(.data=combos, .margins=2, .fun=TabelFn, .expand=TRUE)
library(xtable)

The list Table has three contingency tables in this case and I can sweave the output to LaTex using this code:

<< label = tabTable, echo = FALSE, results = tex >>=
print(xtable(Table[1]$'1', caption = "Contingency table for agegp and alcgp", label = "tab:Table[1]",
             digits = c(0, rep(0, ncol(Table[1]$'1'))),
             align = paste(paste("l|", paste(rep("r", ncol(Table[1]$'1')-1), collapse =     ''), sep = ""), "l", sep = "")),
      table.placement = "tbp", caption.placement = "top",
      hline.after = c(-1, 0, nrow(Table[1]$'1')))
@

To send the output of three contingency tables I've to write three such commands. In this case it is feasible. But for my actual data I've many contingency tables. I'd like to know how to send all contingency tables more efficiently. One choice is to just print the list Table without xtable. But I'd like to have the contingency table in nice output format. Thanks for your time and help.


Solution

  • I needed some mock data to work with

    Data <- data.frame(a=rbinom(100,1,0.5), b=rbinom(100,1,0.3), c=rbinom(100,1,0.6))
    

    With your code to generate Table, this will get you close

    l_ply(Table, function(TBL) {
      print(xtable(TBL, 
          caption = "Contingency table for agegp and alcgp", #This information is not in the TBL anywhere
          label = "tab:Table[1]", # This is also problematic
          digits = c(0, rep(0, ncol(TBL))),
        align = paste(paste("l|", paste(rep("r", ncol(TBL)-1), collapse = ''), sep = ""), "l", sep = "")),
        table.placement = "tbp",
        caption.placement = "top",
        hline.after = c(-1, 0, nrow(TBL)))  
    })
    

    You can get the label right by iterating over an index of Table rather than Table itself

    a_ply(seq_along(Table), 1, function(i) {
      print(xtable(Table[[i]], 
          caption = "Contingency table for agegp and alcgp", #This information is not in the Table[[i]] anywhere
          label = paste("tab:Table[",i,"]",sep=""), 
          digits = c(0, rep(0, ncol(Table[[i]]))),
        align = paste(paste("l|", paste(rep("r", ncol(Table[[i]])-1), collapse = ''), sep = ""), "l", sep = "")),
        table.placement = "tbp",
        caption.placement = "top",
        hline.after = c(-1, 0, nrow(Table[[i]])))       
    })
    

    The caption can not be made automatically because the information is not there. However, if you modify your TableFn function, you can add that information and then extract it back out.

    TabelFn <- function(x) {
      Table <- addmargins(table(Data[, x[1]], Data[, x[2]]))
      names(attr(Table,"dimnames")) <- names(Data)[x]
      return(Table)
    }
    
    Table <- alply(.data=combos, .margins=2, .fun=TabelFn, .expand=TRUE)
    
    a_ply(seq_along(Table), 1, function(i) {
      vars <- names(attr(Table[[i]],"dimnames"))
      print(xtable(Table[[i]], 
          caption = paste("Contingency table for", vars[1], "and", vars[2]),
          label = paste("tab:Table[",i,"]",sep=""), # This is also problematic
          digits = c(0, rep(0, ncol(Table[[i]]))),
        align = paste(paste("l|", paste(rep("r", ncol(Table[[i]])-1), collapse = ''), sep = ""), "l", sep = "")),
        table.placement = "tbp",
        caption.placement = "top",
        hline.after = c(-1, 0, nrow(Table[[i]])))       
    })