Define a macro
defmacro
define a macro that uses R expression replacement
strmacro
define a macro that uses string replacement
defmacro(..., expr) strmacro(..., expr, strexpr)
... |
macro argument list |
expr |
R expression defining the macro body |
strexpr |
character string defining the macro body |
defmacro
and strmacro
create a macro from the expression
given in expr
, with formal arguments given by the other
elements of the argument list.
A macro is similar to a function definition except for handling of
formal arguments. In a function, formal arguments are simply
variables that contains the result of evaluating the expressions
provided to the function call. In contrast, macros actually modify
the macro body by replacing each formal argument by the
expression (defmacro
) or string (strmacro
) provided to
the macro call.
For defmacro
, the special argument name DOTS
will be
replaced by ...
in the formal argument list of the macro so
that ...
in the body of the expression can be used to obtain
any additional arguments passed to the macro. For strmacro
you
can mimic this behavior providing a DOTS=""
argument. This is
illustrated by the last example below.
Macros are often useful for creating new functions during code execution.
A macro function.
Note that because [the defmacro code] works on the parsed expression,
not on a text string, defmacro avoids some of the problems of
traditional string substitution macros such as strmacro
and the C
preprocessor macros. For example, in
mul <- defmacro(a, b, expr={a*b})
a C programmer might expect
mul(i, j + k)
to expand (incorrectly) to i*j + k
. In fact it
expands correctly, to the equivalent of i*(j + k)
.
For a discussion of the differences between functions and macros, please Thomas Lumley's R-News article (reference below).
Thomas Lumley wrote defmacro
. Gregory R. Warnes
greg@warnes.net enhanced it and created
strmacro
.
The original defmacro
code was directly taken from:
Lumley T. "Programmer's Niche: Macros in R", R News, 2001, Vol 1, No. 3, pp 11–13, https://cran.r-project.org/doc/Rnews/
#### # macro for replacing a specified missing value indicator with NA # within a dataframe ### setNA <- defmacro(df, var, values, expr={ df$var[df$var %in% values] <- NA }) # create example data using 999 as a missing value indicator d <- data.frame( Grp=factor(c("Trt", "Ctl", "Ctl", "Trt", "Ctl", "Ctl", "Trt", "Ctl", "Trt", "Ctl")), V1=c(1, 2, 3, 4, 5, 6, 999, 8, 9, 10), V2=c(1, 1, 1, 1, 1, 2, 999, 2, 999, 999) ) d # Try it out setNA(d, V1, 999) setNA(d, V2, 999) d ### # Expression macro ### plot.d <- defmacro( df, var, DOTS, col="red", title="", expr= plot( df$var ~ df$Grp, type="b", col=col, main=title, ... ) ) plot.d( d, V1) plot.d( d, V1, col="blue" ) plot.d( d, V1, lwd=4) # use optional 'DOTS' argument ### # String macro (note the quoted text in the calls below) # # This style of macro can be useful when you are reading # function arguments from a text file ### plot.s <- strmacro( DF, VAR, COL="'red'", TITLE="''", DOTS="", expr= plot( DF$VAR ~ DF$Grp, type="b", col=COL, main=TITLE, DOTS) ) plot.s( "d", "V1") plot.s( DF="d", VAR="V1", COL='"blue"' ) plot.s( "d", "V1", DOTS='lwd=4') # use optional 'DOTS' argument ####### # Create a macro that defines new functions ###### plot.sf <- defmacro(type='b', col='black', title=deparse(substitute(x)), DOTS, expr= function(x,y) plot( x,y, type=type, col=col, main=title, ...) ) plot.red <- plot.sf(col='red',title='Red is more Fun!') plot.blue <- plot.sf(col='blue',title="Blue is Best!", lty=2) plot.red(1:100,rnorm(100)) plot.blue(1:100,rnorm(100))
Please choose more modern alternatives, such as Google Chrome or Mozilla Firefox.