Search code examples
rknitrxtable

Sanitize column names for Bold and Identity with xtable in knitr


Is there a way to pass xtable's identity function to sanitize the column names AND another custom function to bold the column names? There are two code chunks below, one to set up the dummy function and then another to print the xtable. It fails on the $ symbol in the first column name and the $ symbol in the table value is properly sanitized.

Thanks!

<<setup>>=
library(knitr)
library(xtable)
two_functions = function(x){
  paste("\\textbf{", x, "}", sep = "")
  # use xtable's 'identity' function to convert special characters
}

options(xtable.sanitize.colnames.function = two_functions)
@

<<xtable, results='asis'>>=
xtab = data.frame(a = c("Horse and $buddy", "Paddy Wagon", "Hospital Care", "Peanut butter and toast", "Cheese Whiz with Mayo"),
                  b = c(10000000, 200000.4533, 3098765435.65456, 408765467.654456, 50.00000))
colnames(xtab) = c("Hello money $ bag$", "Numbers")
print(xtable(xtab))
@

Solution

  • I think the solution maybe as simple as using gsub within the two_functions call.

    \documentclass{article}
    \begin{document}
    <<<setup>>=
    library(knitr)
    library(xtable)
    
    two_functions = function(x){
        gsub("\\$", "\\\\$", paste("\\textbf{", x, "}", sep = ""))
    }
    
    options(xtable.sanitize.colnames.function = two_functions,
            xtable.sanitize.rownames.function = NULL,
            xtable.sanitize.text.function     = NULL)
    
    @
    
    <<xtable, results='asis'>>=
    xtab = data.frame(a = c("Horse and $buddy", "Paddy Wagon", "Hospital Care", "Peanut butter and toast", "Cheese Whiz with Mayo"),
                      b = c(10000000, 200000.4533, 3098765435.65456, 408765467.654456, 50.00000))
    colnames(xtab) = c("Hello money $ bag$", "Numbers")
    print(xtable(xtab))
    @
    \end{document}
    

    enter image description here

    Edit

    To use the default xtable function for sanitizing a string replace the two_functions function above with the following:

    two_functions = function(x){
      paste0("\\textbf{", xtable::sanitize(x, type = "latex"), "}")
    }
    

    Here the xtable::sanitize function is called first and then the resulting stings are placed inside of the LaTeX \textbf{} environment.

    The resulting table is:

    enter image description here