Writing a ConTeXt module for R
Since I sometimes use the open-source statistics environment R (http://www.r-project.org) as well as ConTeXt, I thought a module that could typeset R code as well as evaluate it on the fly would be useful. Borrowing largely without understanding but lots of trial and eror from m-gnustep.tex, I came up with the attached. Limited testing indicates it works, but at least one problem is apparent: the R code snippets have one unnecessary line break to start them and two after the end. How can I fix that? Of course, any other suggestions are also welcome. A recent R needs to be in the path, but given that, it seems to work on Windows XP as well as Linux. Regards, Johan PS Emacs users may appreciate the following to get r-mode where appropriate: (require 'mmm-mode) (setq mmm-global-mode 'maybe) (setq mmm-submode-decoration-level 2) (mmm-add-group 'context-plus '((context-MP :submode metapost-mode :face mmm-code-submode-face :front ".*\\\\start\\w*MP\\w*\\({\\w*}\\|\\[\\w*\\]\\|\\)\\W" :back ".*\\\\stop\\w*MP") (context-R :submode r-mode :face mmm-comment-submode-face :front ".*\\\\startR.*\\W" :back ".*\\\\stopR.*"))) (add-to-list 'mmm-mode-ext-classes-alist '(context-mode nil context-plus)) -- Johan Sandblom N8, MRC, Karolinska sjh t +46851776108 17176 Stockholm m +46735521477 Sweden "What is wanted is not the will to believe, but the will to find out, which is the exact opposite" - Bertrand Russell
Attachment seems to have failed I put the content of the file below.
2006/6/6, Johan Sandblom
Since I sometimes use the open-source statistics environment R (http://www.r-project.org) as well as ConTeXt, I thought a module that could typeset R code as well as evaluate it on the fly would be useful. Borrowing largely without understanding but lots of trial and eror from m-gnustep.tex, I came up with the attached. Limited testing indicates it works, but at least one problem is apparent: the R code snippets have one unnecessary line break to start them and two after the end. How can I fix that? Of course, any other suggestions are also welcome.
A recent R needs to be in the path, but given that, it seems to work on Windows XP as well as Linux.
Regards, Johan
PS Emacs users may appreciate the following to get r-mode where appropriate: (require 'mmm-mode) (setq mmm-global-mode 'maybe) (setq mmm-submode-decoration-level 2) (mmm-add-group 'context-plus '((context-MP :submode metapost-mode :face mmm-code-submode-face :front ".*\\\\start\\w*MP\\w*\\({\\w*}\\|\\[\\w*\\]\\|\\)\\W" :back ".*\\\\stop\\w*MP") (context-R :submode r-mode :face mmm-comment-submode-face :front ".*\\\\startR.*\\W" :back ".*\\\\stopR.*"))) (add-to-list 'mmm-mode-ext-classes-alist '(context-mode nil context-plus))
-- Johan Sandblom N8, MRC, Karolinska sjh t +46851776108 17176 Stockholm m +46735521477 Sweden "What is wanted is not the will to believe, but the will to find out, which is the exact opposite" - Bertrand Russell
% Copyright Johan Sandblom, distributed and redistributable under the % terms of the GNU Lesser General Public License. \unprotect \newcounter\Rnumber % I would like to reduce this two-stage call, but then line-endings disappear \def\startR% {\bgroup \obeylines \catcode`\%=\@@letter \catcode`\#=\@@letter \dostartR% }% \def\dostartR#1\stopR% {\doglobal\increment\Rnumber% \letgvalue{rcs:n:\Rnumber}\Rnumber% \setgvalue{rcs:d:\Rnumber}{#1}% \edef\Rfile {\bufferprefix R-\Rnumber}% \bgroup% \the\everyR% \immediate\openout\scratchwrite=\Rfile.r% \def\par{\rawcharacter{10}}% \immediate\write\scratchwrite{\getvalue{rcs:d:\Rnumber}}% \immediate\closeout\scratchwrite% \egroup% \startmode[*\v!first]% \runR% \stopmode \typeRout% \egroup}% \def\startRhidden% {\bgroup \obeylines \catcode`\%=\@@letter \dostartRhidden{}} \def\dostartRhidden#1\stopRhidden {\doglobal\increment\Rnumber \letgvalue{rcs:n:\Rnumber}\Rnumber \setgvalue{rcs:d:\Rnumber}{#1}% \edef\Rfile {\bufferprefix R-\Rnumber}% \bgroup \the\everyR% \immediate\openout\scratchwrite=\Rfile.r% \def\par{\rawcharacter{10}}% \immediate\write\scratchwrite{\getvalue{rcs:d:\Rnumber}}% \immediate\closeout\scratchwrite% \egroup \startmode[*\v!first]% \runR% \stopmode \egroup} \newtoks\everyR \appendtoks \obeylines \to \everyR % The call to R has -q in order to prevent banner, --save to make sure % it saves the workspace after the run, --restore to make sure it % reads any workspace from a previous session \def\runR {\executesystemcommand{R -q --save --restore < \Rfile.r > \Rfile.Rout}} \def\typeRout {\typefile{\Rfile.Rout}} \protect \doifnotmode{demo}{\endinput} \starttext \startR a <- "bla" b <- "blabla" ls() \stopR bla bla \startRhidden rm(list=ls()) save.image() \stopRhidden bla \startR ls() ushape <- c(rexp(500000), 12-rexp(500000)) pdf("ushape.pdf") par(mfrow=c(1,2)) hist(ushape) plot(density(ushape), main="Density") dev.off() \stopR \input tufte \input knuth \startR x <- rnorm(900) y <- rexp(900) # test comment f <- gl(9,9,900) summary(aov(y~x+Error(f))) library(lattice) pdf("lattice.pdf") xyplot(y~x|f) dev.off() \stopR \placefigure[here]{}{\externalfigure[lattice]} \placefigure[here]{}{\externalfigure[ushape]} \input tufte \startR (test <- ".*\\\\ []{}=?!+%#|<|>@$") cat(test) \stopR \input bryson \input knuth \startR a.df <- data.frame(a=1:2, b=rnorm(2)) a.df$a testfunction <- function(a=NULL, ...) { for(i in 1:length(a)) { gsub(a[[i]], "([a-r]|[A-R])", "bla")} print(a)} \stopR \stoptext -- Johan Sandblom N8, MRC, Karolinska sjh t +46851776108 17176 Stockholm m +46735521477 Sweden "What is wanted is not the will to believe, but the will to find out, which is the exact opposite" - Bertrand Russell
I do not have R installed here. but: Johan Sandblom wrote:
% I would like to reduce this two-stage call, but then line-endings disappear
This two-stage approach is required unless each statement in R is terminated uniquely, by something like a semicolon because then you could redefine the semicolon at the writing stage.
\def\startR% {\bgroup \obeylines \catcode`\%=\@@letter \catcode`\#=\@@letter \dostartR% }%
Don't you need percent signs at the end of the @@letter lines?
\stopmode \typeRout% \egroup}%
You can make that \stopmode \egroup \typeRout } because \typefile doesnt need \obeylines Cheers, Taco
Thank you for your explanations, and yes I probably do need percent
signs if my test case had been more severe. Hans, with characteristic
swiftness, already sent me back a vastly improved version which I will
test as soon as I get a chance.
Johan
2006/6/7, Taco Hoekwater
I do not have R installed here. but:
Johan Sandblom wrote:
% I would like to reduce this two-stage call, but then line-endings disappear
This two-stage approach is required unless each statement in R is terminated uniquely, by something like a semicolon because then you could redefine the semicolon at the writing stage.
\def\startR% {\bgroup \obeylines \catcode`\%=\@@letter \catcode`\#=\@@letter \dostartR% }%
Don't you need percent signs at the end of the @@letter lines?
\stopmode \typeRout% \egroup}%
You can make that
\stopmode \egroup \typeRout }
because \typefile doesnt need \obeylines
Cheers, Taco
-- Johan Sandblom N8, MRC, Karolinska sjh t +46851776108 17176 Stockholm m +46735521477 Sweden "What is wanted is not the will to believe, but the will to find out, which is the exact opposite" - Bertrand Russell
participants (2)
-
Johan Sandblom
-
Taco Hoekwater