SlideShare a Scribd company logo
Rcpp: Seamless R and C++

         Romain François            Dirk Eddelbuettel
 romain@r-enthusiasts.com           edd@debian.org




LondonR, Oct 05th , Counting House - 50 Cornhill, London.
Fine for Indiana Jones
Le viaduc de Millau
Background API Sugar Modules




                                     Plat du jour

1   Appetizers : Some background on R and C++

2   Main course : The Rcpp API

3   Desert : Rcpp sugar

4   Coffee : Rcpp modules




        Dirk Eddelbuettel and Romain François   Seamless R anc C++ Integration @ LondonR/Oct 2010
Background API Sugar Modules          Overview Examples

R support for C/C++


     R is a C program
     R supports C++ out of the box, just use a .cpp file extension
     R exposes a API based on low level C functions and MACROS.
     R provides several calling conventions to invoke compiled code.


  SEXP foo( SEXP x1, SEXP x2 ){
     ...
  }


  > .Call( "foo", 1:10, rnorm(10) )



         Dirk Eddelbuettel and Romain François   Seamless R anc C++ Integration @ LondonR/Oct 2010
Background API Sugar Modules          Overview Examples

.Call example
  #include <R.h>
  #include <Rdefines.h>
  extern "C"SEXP vectorfoo(SEXP a, SEXP b){
    int i, n;
    double *xa, *xb, *xab; SEXP ab;
    PROTECT(a = AS_NUMERIC(a));
    PROTECT(b = AS_NUMERIC(b));
    n = LENGTH(a);
    PROTECT(ab = NEW_NUMERIC(n));
    xa=NUMERIC_POINTER(a); xb=NUMERIC_POINTER(b);
    xab = NUMERIC_POINTER(ab);
    double x = 0.0, y = 0.0 ;
    for (i=0; i<n; i++) xab[i] = 0.0;
    for (i=0; i<n; i++) {
       x = xa[i]; y = xb[i];
       res[i] = (x < y) ? x*x : -(y*y);
    }
    UNPROTECT(3);
    return(ab);
  }

         Dirk Eddelbuettel and Romain François   Seamless R anc C++ Integration @ LondonR/Oct 2010
Background API Sugar Modules          Overview Examples

.Call example: character vectors


  > c( "foo", "bar" )

  #include <R.h>
  #include <Rdefines.h>
  extern "C"SEXP foobar(){
    SEXP res = PROTECT(allocVector(STRSXP, 2));
    SET_STRING_ELT( res, 0, mkChar( "foo") ) ;
    SET_STRING_ELT( res, 1, mkChar( "bar") ) ;
    UNPROTECT(1) ;
    return res ;
  }




        Dirk Eddelbuettel and Romain François   Seamless R anc C++ Integration @ LondonR/Oct 2010
Background API Sugar Modules          Overview Examples

.Call example: calling an R function
  > eval( call( "rnorm", 3L, 10.0, 20.0 ) )

  #include <R.h>
  #include <Rdefines.h>
  extern "C"SEXP callback(){
    SEXP call = PROTECT( LCONS( install("rnorm"),
       CONS( ScalarInteger( 3 ),
          CONS( ScalarReal( 10.0 ),
           CONS( ScalarReal( 20.0 ), R_NilValue )
        )
      )
    ) );
    SEXP res = PROTECT(eval(call, R_GlobalEnv)) ;
    UNPROTECT(2) ;
    return res ;
  }

        Dirk Eddelbuettel and Romain François   Seamless R anc C++ Integration @ LondonR/Oct 2010
The Rcpp API
Background API Sugar Modules          Overview Example Conversion

The Rcpp API



     Encapsulation of R objects (SEXP) into C++ classes:
     NumericVector, IntegerVector, ..., Function,
     Environment, Language, ...

     Conversion from R to C++ : as

     Conversion from C++ to R : wrap

     Interoperability with the Standard Template Library (STL)




        Dirk Eddelbuettel and Romain François   Seamless R anc C++ Integration @ LondonR/Oct 2010
Background API Sugar Modules          Overview Example Conversion

The Rcpp API : classes


            Rcpp class                                    R typeof
     Integer(Vector|Matrix)                      integer vectors and matrices
     Numeric(Vector|Matrix)                              numeric ...
     Logical(Vector|Matrix)                              logical ...
    Character(Vector|Matrix)                            character ...
       Raw(Vector|Matrix)                                  raw ...
     Complex(Vector|Matrix)                              complex ...
               List                              list (aka generic vectors) ...
   Expression(Vector|Matrix)                           expression ...
           Environment                                 environment
            Function                                     function
               XPtr                                    externalptr
            Language                                     language
                S4                                           S4
                ...                                          ...

        Dirk Eddelbuettel and Romain François   Seamless R anc C++ Integration @ LondonR/Oct 2010
Background API Sugar Modules          Overview Example Conversion

The Rcpp API : example


  SEXP foo( SEXP xs, SEXP ys ){
      Rcpp::NumericVector xx(xs), yy(ys) ;
      int n = xx.size() ;
      Rcpp::NumericVector res( n ) ;
      double x = 0.0, y = 0.0 ;
      for (int i=0; i<n; i++) {
           x = xx[i];
           y = yy[i];
           res[i] = (x < y) ? x*x : -(y*y);
      }
      return res ;
  }




        Dirk Eddelbuettel and Romain François   Seamless R anc C++ Integration @ LondonR/Oct 2010
Background API Sugar Modules          Overview Example Conversion

The Rcpp API : example


  using namespace Rcpp ;
  SEXP bar(){
       std::vector<double> z(10) ;
       List res = List::create(
          _["foo"] = NumericVector::create(1,2),
          _["bar"] = 3,
          _["bla"] = "yada yada",
          _["blo"] = z
          ) ;
       res.attr("class") = "myclass";
       return res ;
  }




        Dirk Eddelbuettel and Romain François   Seamless R anc C++ Integration @ LondonR/Oct 2010
Background API Sugar Modules        Overview Example Conversion

The Rcpp API : conversion from R to C++

  Rcpp::as<T> handles conversion from SEXP to T.

  template <typename T> T as( SEXP m_sexp)
      throw(not_compatible) ;

  T can be:
      primitive type : int, double, bool, long, std::string
      any type that has a constructor taking a SEXP
      ... that specializes the as template
      ... that specializes the Exporter class template
      containers from the STL
  more details in the Rcpp-extending vignette.


          Dirk Eddelbuettel and Romain François   Seamless R anc C++ Integration @ LondonR/Oct 2010
Background API Sugar Modules        Overview Example Conversion

The Rcpp API : conversion from C++ to R

  Rcpp::wrap<T> handles conversion from T to SEXP.

  template <typename T>
  SEXP wrap( const T& object ) ;

  T can be:
      primitive type : int, double, bool, long, std::string
      any type that has a an operator SEXP
      ... that specializes the wrap template
      ... that has a nested type called iterator and member
      functions begin and end
      containers from the STL vector<T>, list<T>,
      map<string,T>, etc ... (where T is itself wrappable)
  more details in the Rcpp-extending vignette.

          Dirk Eddelbuettel and Romain François   Seamless R anc C++ Integration @ LondonR/Oct 2010
Background API Sugar Modules          Overview Example Conversion

The Rcpp API : conversion examples

  typedef std::vector<double> Vec ;
  int x_= as<int>( x ) ;
  double y_= as<double>( y_) ;
  VEC z_= as<VEC>( z_) ;

  wrap( 1 ) ; // INTSXP
  wrap( "foo") ; // STRSXP

  typedef std::map<std::string,Vec> Map ;
  Map foo( 10 ) ;
  Vec f1(4) ;
  Vec f2(10) ;
  foo.insert( "x", f1 ) ;
  foo.insert( "y", f2 ) ;
  wrap( foo ) ; // named list of numeric vectors


         Dirk Eddelbuettel and Romain François   Seamless R anc C++ Integration @ LondonR/Oct 2010
Background API Sugar Modules          Overview Example Conversion

The Rcpp API : implicit conversion examples


  Environment env = ... ;
  List list = ... ;
  Function rnorm( "rnorm") ;

  // implicit calls to as
  int x = env["x"] ;
  double y = list["y"];

  // implicit calls to wrap
  rnorm( 100, _["mean"] = 10 ) ;
  env["x"] = 3;
  env["y"] = "foo";
  List::create( 1, "foo", 10.0, false ) ;




        Dirk Eddelbuettel and Romain François   Seamless R anc C++ Integration @ LondonR/Oct 2010
Rcpp sugar
Background API Sugar Modules          Motivation Example Contents Performance

Sugar : motivation


  int n = x.size() ;
  NumericVector res1( n ) ;
  double x_= 0.0, y_= 0.0 ;
  for( int i=0; i<n; i++){
           x_= x[i] ;y_= y[i] ;
           if( R_IsNA(x_) ||R_IsNA(y_) ){
                res1[i] = NA_REAL;
           } else if( x_< y_){
                res1[i] = x_* x_;
           } else {
                res1[i] = -( y_* y_) ;
           }
       }




        Dirk Eddelbuettel and Romain François   Seamless R anc C++ Integration @ LondonR/Oct 2010
Background API Sugar Modules          Motivation Example Contents Performance

Sugar : motivation


  We missed the R syntax :
  > ifelse( x < y, x*x, -(y*y) )




         Dirk Eddelbuettel and Romain François   Seamless R anc C++ Integration @ LondonR/Oct 2010
Background API Sugar Modules          Motivation Example Contents Performance

Sugar : motivation


  We missed the R syntax :
  > ifelse( x < y, x*x, -(y*y) )


  sugar brings it into C++

  SEXP foo( SEXP xx, SEXP yy){
      NumericVector x(xx), y(yy) ;
      return ifelse( x < y, x*x, -(y*y) ) ;
  }




          Dirk Eddelbuettel and Romain François   Seamless R anc C++ Integration @ LondonR/Oct 2010
Background API Sugar Modules          Motivation Example Contents Performance

Sugar : another example



  double square( double x){
    return x*x ;
  }

  SEXP foo( SEXP xx ){
    NumericVector x(xx) ;
    return sapply( x, square ) ;
  }




        Dirk Eddelbuettel and Romain François   Seamless R anc C++ Integration @ LondonR/Oct 2010
Background API Sugar Modules          Motivation Example Contents Performance

Sugar : contents


      logical operators: <, >, <=, >=, ==, !=
      arithmetic operators: +, -, *, /
      functions on vectors: abs, all, any, ceiling, diag,
      diff, exp, head, ifelse, is_na, lapply, pmin, pmax,
      pow, rep, rep_each, rep_len, rev, sapply,
      seq_along, seq_len, sign, tail
      functions on matrices: outer, col, row, lower_tri,
      upper_tri, diag
      statistical functions (dpqr) : rnorm, dpois, qlogis, etc ...


  More information in the Rcpp-sugar vignette.


          Dirk Eddelbuettel and Romain François   Seamless R anc C++ Integration @ LondonR/Oct 2010
Background API Sugar Modules                Motivation Example Contents Performance

Sugar : benchmarks



    expression                                                         sugar              R          R / sugar
    any(x*y<0)                                                     0.000447              4.86       10867

    ifelse(x<y,x*x,-(y*y))                                         1.331               22.29             16.74
                                                       ( )
    ifelse(x<y,x*x,-(y*y))                                         0.832               21.59             24.19

    sapply(x,square)                                               0.240              138.71            577.39

  Benchmarks performed on OSX SL / R 2.12.0 alpha (64 bit) on a MacBook Pro (i5).




   : version includes optimization related to the absence of missing values




                Dirk Eddelbuettel and Romain François         Seamless R anc C++ Integration @ LondonR/Oct 2010
Background API Sugar Modules                Motivation Example Contents Performance

Sugar : benchmarks

  Benchmarks of the convolution example from Writing R
  Extensions.

            Implementation                                                Time in         Relative
                                                                          millisec        to R API
            R API (as benchmark)                                                218
            Rcpp sugar                                                          145              0.67
            NumericVector::iterator                                             217              1.00
            NumericVector::operator[]                                           282              1.29
            RcppVector<double>                                                  683              3.13

     Table: Convolution of x and y (200 values), repeated 5000 times.


  Extract from the article Rcpp: Seamless R and C++ integration, accepted for publication in the R Journal.




                 Dirk Eddelbuettel and Romain François         Seamless R anc C++ Integration @ LondonR/Oct 2010
Rcpp modules
Background API Sugar Modules          Overview R side

Modules: expose C++ to R


  const char* hello( const std::string& who ){
      std::string result( "hello ") ;
      result += who ;
      return result.c_str() ;
  }

  RCPP_MODULE(yada){
      using namespace Rcpp ;
      function( "hello", &hello ) ;
  }


  > yada <- Module( "yada" )
  > yada$hello( "world" )



        Dirk Eddelbuettel and Romain François   Seamless R anc C++ Integration @ LondonR/Oct 2010
Background API Sugar Modules          Overview R side

Modules: expose C++ classes to R

  class World {
  public:
       World() : msg("hello"){}
       void set(std::string msg) {
           this->msg = msg;
       }
       std::string greet() {
           return msg;
       }
  private:
       std::string msg;
  };

  void clearWorld( World* w){
      w->set( "") ;
  }


        Dirk Eddelbuettel and Romain François   Seamless R anc C++ Integration @ LondonR/Oct 2010
Background API Sugar Modules          Overview R side

Modules: expose C++ classes to R


  C++ side: declare what to expose

  RCPP_MODULE(yada){
      using namespace Rcpp ;

       class_<World>( "World")
           .method( "greet", &World::greet )
           .method( "set", &World::set )
           .method( "clear", &clearWorld )
       ;

  }




          Dirk Eddelbuettel and Romain François   Seamless R anc C++ Integration @ LondonR/Oct 2010
Background API Sugar Modules          Overview R side

Modules: on the R side
  R side: based on R 2.12.0 reference classes (see
  ?ReferenceClasses)
  > World <- yada$World
  > w <- new( World )
  > w$greet()
  [1] "hello"

  > w$set( "hello world")
  > w$greet()
  [1] "hello world"

  > w$clear()
  > w$greet()
  [1] ""


          Dirk Eddelbuettel and Romain François   Seamless R anc C++ Integration @ LondonR/Oct 2010
Want to learn more ?

  Check the vignettes

  Questions on the Rcpp-devel mailing list

  Hands-on training courses

  Commercial support



Romain François               romain@r-enthusiasts.com
Dirk Eddelbuettel                       edd@debian.org

More Related Content

PDF
Rcpp: Seemless R and C++
PDF
Rcpp: Seemless R and C++
PDF
Scala is java8.next()
PPTX
Basic c++ programs
PPTX
PPT
STL ALGORITHMS
PDF
Javascript engine performance
PPTX
Idiomatic C++
Rcpp: Seemless R and C++
Rcpp: Seemless R and C++
Scala is java8.next()
Basic c++ programs
STL ALGORITHMS
Javascript engine performance
Idiomatic C++

What's hot (20)

PPTX
PDF
C++17 introduction - Meetup @EtixLabs
PDF
Contravariant functors in scala
PDF
Fun with Lambdas: C++14 Style (part 1)
PDF
C++11 concurrency
PPTX
The Style of C++ 11
PPTX
Summary of C++17 features
PPT
Advance LISP (Artificial Intelligence)
PDF
Liszt los alamos national laboratory Aug 2011
PDF
C++20 the small things - Timur Doumler
PDF
Modern c++ (C++ 11/14)
PDF
Introduction To Lisp
PDF
Halogen: Past, Present, and Future
PPT
friends functionToshu
PPTX
Fun with Lambdas: C++14 Style (part 2)
PPTX
basics of c++
PPTX
Introduction to c++
PDF
Garbage Collection
PPTX
C++ 11 Features
PDF
Virtual Functions
C++17 introduction - Meetup @EtixLabs
Contravariant functors in scala
Fun with Lambdas: C++14 Style (part 1)
C++11 concurrency
The Style of C++ 11
Summary of C++17 features
Advance LISP (Artificial Intelligence)
Liszt los alamos national laboratory Aug 2011
C++20 the small things - Timur Doumler
Modern c++ (C++ 11/14)
Introduction To Lisp
Halogen: Past, Present, and Future
friends functionToshu
Fun with Lambdas: C++14 Style (part 2)
basics of c++
Introduction to c++
Garbage Collection
C++ 11 Features
Virtual Functions
Ad

Similar to Rcpp: Seemless R and C++ (20)

PDF
Integrating R with C++: Rcpp, RInside and RProtoBuf
PDF
Rcpp
PDF
Native interfaces for R
PDF
R and C++
PDF
Oh Crap, I Forgot (Or Never Learned) C! [CodeMash 2010]
PDF
R/C++ talk at earl 2014
PDF
Rcpp11 genentech
PDF
Monads in Swift
PPT
C# programming
PDF
Design Patterns - Compiler Case Study - Hands-on Examples
PPTX
Intel JIT Talk
PDF
Translate the following CC++ code into MIPS Assembly Codevoid ch.pdf
PPTX
stack.pptx
PDF
PPT
sonam Kumari python.ppt
PDF
What's new in Apache SystemML - Declarative Machine Learning
PPT
Lex (lexical analyzer)
PDF
Spark workshop
PPTX
Integrating R with C++: Rcpp, RInside and RProtoBuf
Rcpp
Native interfaces for R
R and C++
Oh Crap, I Forgot (Or Never Learned) C! [CodeMash 2010]
R/C++ talk at earl 2014
Rcpp11 genentech
Monads in Swift
C# programming
Design Patterns - Compiler Case Study - Hands-on Examples
Intel JIT Talk
Translate the following CC++ code into MIPS Assembly Codevoid ch.pdf
stack.pptx
sonam Kumari python.ppt
What's new in Apache SystemML - Declarative Machine Learning
Lex (lexical analyzer)
Spark workshop
Ad

More from Romain Francois (15)

PDF
PDF
dplyr and torrents from cpasbien
PDF
dplyr use case
PDF
PDF
user2015 keynote talk
PDF
SevillaR meetup: dplyr and magrittr
PDF
PDF
Data manipulation with dplyr
PDF
Rcpp11 useR2014
PDF
R and cpp
PDF
Rcpp attributes
PDF
Rcpp is-ready
PDF
Object Oriented Design(s) in R
PDF
RProtoBuf: protocol buffers for R
dplyr and torrents from cpasbien
dplyr use case
user2015 keynote talk
SevillaR meetup: dplyr and magrittr
Data manipulation with dplyr
Rcpp11 useR2014
R and cpp
Rcpp attributes
Rcpp is-ready
Object Oriented Design(s) in R
RProtoBuf: protocol buffers for R

Rcpp: Seemless R and C++

  • 1. Rcpp: Seamless R and C++ Romain François Dirk Eddelbuettel romain@r-enthusiasts.com edd@debian.org LondonR, Oct 05th , Counting House - 50 Cornhill, London.
  • 3. Le viaduc de Millau
  • 4. Background API Sugar Modules Plat du jour 1 Appetizers : Some background on R and C++ 2 Main course : The Rcpp API 3 Desert : Rcpp sugar 4 Coffee : Rcpp modules Dirk Eddelbuettel and Romain François Seamless R anc C++ Integration @ LondonR/Oct 2010
  • 5. Background API Sugar Modules Overview Examples R support for C/C++ R is a C program R supports C++ out of the box, just use a .cpp file extension R exposes a API based on low level C functions and MACROS. R provides several calling conventions to invoke compiled code. SEXP foo( SEXP x1, SEXP x2 ){ ... } > .Call( "foo", 1:10, rnorm(10) ) Dirk Eddelbuettel and Romain François Seamless R anc C++ Integration @ LondonR/Oct 2010
  • 6. Background API Sugar Modules Overview Examples .Call example #include <R.h> #include <Rdefines.h> extern "C"SEXP vectorfoo(SEXP a, SEXP b){ int i, n; double *xa, *xb, *xab; SEXP ab; PROTECT(a = AS_NUMERIC(a)); PROTECT(b = AS_NUMERIC(b)); n = LENGTH(a); PROTECT(ab = NEW_NUMERIC(n)); xa=NUMERIC_POINTER(a); xb=NUMERIC_POINTER(b); xab = NUMERIC_POINTER(ab); double x = 0.0, y = 0.0 ; for (i=0; i<n; i++) xab[i] = 0.0; for (i=0; i<n; i++) { x = xa[i]; y = xb[i]; res[i] = (x < y) ? x*x : -(y*y); } UNPROTECT(3); return(ab); } Dirk Eddelbuettel and Romain François Seamless R anc C++ Integration @ LondonR/Oct 2010
  • 7. Background API Sugar Modules Overview Examples .Call example: character vectors > c( "foo", "bar" ) #include <R.h> #include <Rdefines.h> extern "C"SEXP foobar(){ SEXP res = PROTECT(allocVector(STRSXP, 2)); SET_STRING_ELT( res, 0, mkChar( "foo") ) ; SET_STRING_ELT( res, 1, mkChar( "bar") ) ; UNPROTECT(1) ; return res ; } Dirk Eddelbuettel and Romain François Seamless R anc C++ Integration @ LondonR/Oct 2010
  • 8. Background API Sugar Modules Overview Examples .Call example: calling an R function > eval( call( "rnorm", 3L, 10.0, 20.0 ) ) #include <R.h> #include <Rdefines.h> extern "C"SEXP callback(){ SEXP call = PROTECT( LCONS( install("rnorm"), CONS( ScalarInteger( 3 ), CONS( ScalarReal( 10.0 ), CONS( ScalarReal( 20.0 ), R_NilValue ) ) ) ) ); SEXP res = PROTECT(eval(call, R_GlobalEnv)) ; UNPROTECT(2) ; return res ; } Dirk Eddelbuettel and Romain François Seamless R anc C++ Integration @ LondonR/Oct 2010
  • 10. Background API Sugar Modules Overview Example Conversion The Rcpp API Encapsulation of R objects (SEXP) into C++ classes: NumericVector, IntegerVector, ..., Function, Environment, Language, ... Conversion from R to C++ : as Conversion from C++ to R : wrap Interoperability with the Standard Template Library (STL) Dirk Eddelbuettel and Romain François Seamless R anc C++ Integration @ LondonR/Oct 2010
  • 11. Background API Sugar Modules Overview Example Conversion The Rcpp API : classes Rcpp class R typeof Integer(Vector|Matrix) integer vectors and matrices Numeric(Vector|Matrix) numeric ... Logical(Vector|Matrix) logical ... Character(Vector|Matrix) character ... Raw(Vector|Matrix) raw ... Complex(Vector|Matrix) complex ... List list (aka generic vectors) ... Expression(Vector|Matrix) expression ... Environment environment Function function XPtr externalptr Language language S4 S4 ... ... Dirk Eddelbuettel and Romain François Seamless R anc C++ Integration @ LondonR/Oct 2010
  • 12. Background API Sugar Modules Overview Example Conversion The Rcpp API : example SEXP foo( SEXP xs, SEXP ys ){ Rcpp::NumericVector xx(xs), yy(ys) ; int n = xx.size() ; Rcpp::NumericVector res( n ) ; double x = 0.0, y = 0.0 ; for (int i=0; i<n; i++) { x = xx[i]; y = yy[i]; res[i] = (x < y) ? x*x : -(y*y); } return res ; } Dirk Eddelbuettel and Romain François Seamless R anc C++ Integration @ LondonR/Oct 2010
  • 13. Background API Sugar Modules Overview Example Conversion The Rcpp API : example using namespace Rcpp ; SEXP bar(){ std::vector<double> z(10) ; List res = List::create( _["foo"] = NumericVector::create(1,2), _["bar"] = 3, _["bla"] = "yada yada", _["blo"] = z ) ; res.attr("class") = "myclass"; return res ; } Dirk Eddelbuettel and Romain François Seamless R anc C++ Integration @ LondonR/Oct 2010
  • 14. Background API Sugar Modules Overview Example Conversion The Rcpp API : conversion from R to C++ Rcpp::as<T> handles conversion from SEXP to T. template <typename T> T as( SEXP m_sexp) throw(not_compatible) ; T can be: primitive type : int, double, bool, long, std::string any type that has a constructor taking a SEXP ... that specializes the as template ... that specializes the Exporter class template containers from the STL more details in the Rcpp-extending vignette. Dirk Eddelbuettel and Romain François Seamless R anc C++ Integration @ LondonR/Oct 2010
  • 15. Background API Sugar Modules Overview Example Conversion The Rcpp API : conversion from C++ to R Rcpp::wrap<T> handles conversion from T to SEXP. template <typename T> SEXP wrap( const T& object ) ; T can be: primitive type : int, double, bool, long, std::string any type that has a an operator SEXP ... that specializes the wrap template ... that has a nested type called iterator and member functions begin and end containers from the STL vector<T>, list<T>, map<string,T>, etc ... (where T is itself wrappable) more details in the Rcpp-extending vignette. Dirk Eddelbuettel and Romain François Seamless R anc C++ Integration @ LondonR/Oct 2010
  • 16. Background API Sugar Modules Overview Example Conversion The Rcpp API : conversion examples typedef std::vector<double> Vec ; int x_= as<int>( x ) ; double y_= as<double>( y_) ; VEC z_= as<VEC>( z_) ; wrap( 1 ) ; // INTSXP wrap( "foo") ; // STRSXP typedef std::map<std::string,Vec> Map ; Map foo( 10 ) ; Vec f1(4) ; Vec f2(10) ; foo.insert( "x", f1 ) ; foo.insert( "y", f2 ) ; wrap( foo ) ; // named list of numeric vectors Dirk Eddelbuettel and Romain François Seamless R anc C++ Integration @ LondonR/Oct 2010
  • 17. Background API Sugar Modules Overview Example Conversion The Rcpp API : implicit conversion examples Environment env = ... ; List list = ... ; Function rnorm( "rnorm") ; // implicit calls to as int x = env["x"] ; double y = list["y"]; // implicit calls to wrap rnorm( 100, _["mean"] = 10 ) ; env["x"] = 3; env["y"] = "foo"; List::create( 1, "foo", 10.0, false ) ; Dirk Eddelbuettel and Romain François Seamless R anc C++ Integration @ LondonR/Oct 2010
  • 19. Background API Sugar Modules Motivation Example Contents Performance Sugar : motivation int n = x.size() ; NumericVector res1( n ) ; double x_= 0.0, y_= 0.0 ; for( int i=0; i<n; i++){ x_= x[i] ;y_= y[i] ; if( R_IsNA(x_) ||R_IsNA(y_) ){ res1[i] = NA_REAL; } else if( x_< y_){ res1[i] = x_* x_; } else { res1[i] = -( y_* y_) ; } } Dirk Eddelbuettel and Romain François Seamless R anc C++ Integration @ LondonR/Oct 2010
  • 20. Background API Sugar Modules Motivation Example Contents Performance Sugar : motivation We missed the R syntax : > ifelse( x < y, x*x, -(y*y) ) Dirk Eddelbuettel and Romain François Seamless R anc C++ Integration @ LondonR/Oct 2010
  • 21. Background API Sugar Modules Motivation Example Contents Performance Sugar : motivation We missed the R syntax : > ifelse( x < y, x*x, -(y*y) ) sugar brings it into C++ SEXP foo( SEXP xx, SEXP yy){ NumericVector x(xx), y(yy) ; return ifelse( x < y, x*x, -(y*y) ) ; } Dirk Eddelbuettel and Romain François Seamless R anc C++ Integration @ LondonR/Oct 2010
  • 22. Background API Sugar Modules Motivation Example Contents Performance Sugar : another example double square( double x){ return x*x ; } SEXP foo( SEXP xx ){ NumericVector x(xx) ; return sapply( x, square ) ; } Dirk Eddelbuettel and Romain François Seamless R anc C++ Integration @ LondonR/Oct 2010
  • 23. Background API Sugar Modules Motivation Example Contents Performance Sugar : contents logical operators: <, >, <=, >=, ==, != arithmetic operators: +, -, *, / functions on vectors: abs, all, any, ceiling, diag, diff, exp, head, ifelse, is_na, lapply, pmin, pmax, pow, rep, rep_each, rep_len, rev, sapply, seq_along, seq_len, sign, tail functions on matrices: outer, col, row, lower_tri, upper_tri, diag statistical functions (dpqr) : rnorm, dpois, qlogis, etc ... More information in the Rcpp-sugar vignette. Dirk Eddelbuettel and Romain François Seamless R anc C++ Integration @ LondonR/Oct 2010
  • 24. Background API Sugar Modules Motivation Example Contents Performance Sugar : benchmarks expression sugar R R / sugar any(x*y<0) 0.000447 4.86 10867 ifelse(x<y,x*x,-(y*y)) 1.331 22.29 16.74 ( ) ifelse(x<y,x*x,-(y*y)) 0.832 21.59 24.19 sapply(x,square) 0.240 138.71 577.39 Benchmarks performed on OSX SL / R 2.12.0 alpha (64 bit) on a MacBook Pro (i5). : version includes optimization related to the absence of missing values Dirk Eddelbuettel and Romain François Seamless R anc C++ Integration @ LondonR/Oct 2010
  • 25. Background API Sugar Modules Motivation Example Contents Performance Sugar : benchmarks Benchmarks of the convolution example from Writing R Extensions. Implementation Time in Relative millisec to R API R API (as benchmark) 218 Rcpp sugar 145 0.67 NumericVector::iterator 217 1.00 NumericVector::operator[] 282 1.29 RcppVector<double> 683 3.13 Table: Convolution of x and y (200 values), repeated 5000 times. Extract from the article Rcpp: Seamless R and C++ integration, accepted for publication in the R Journal. Dirk Eddelbuettel and Romain François Seamless R anc C++ Integration @ LondonR/Oct 2010
  • 27. Background API Sugar Modules Overview R side Modules: expose C++ to R const char* hello( const std::string& who ){ std::string result( "hello ") ; result += who ; return result.c_str() ; } RCPP_MODULE(yada){ using namespace Rcpp ; function( "hello", &hello ) ; } > yada <- Module( "yada" ) > yada$hello( "world" ) Dirk Eddelbuettel and Romain François Seamless R anc C++ Integration @ LondonR/Oct 2010
  • 28. Background API Sugar Modules Overview R side Modules: expose C++ classes to R class World { public: World() : msg("hello"){} void set(std::string msg) { this->msg = msg; } std::string greet() { return msg; } private: std::string msg; }; void clearWorld( World* w){ w->set( "") ; } Dirk Eddelbuettel and Romain François Seamless R anc C++ Integration @ LondonR/Oct 2010
  • 29. Background API Sugar Modules Overview R side Modules: expose C++ classes to R C++ side: declare what to expose RCPP_MODULE(yada){ using namespace Rcpp ; class_<World>( "World") .method( "greet", &World::greet ) .method( "set", &World::set ) .method( "clear", &clearWorld ) ; } Dirk Eddelbuettel and Romain François Seamless R anc C++ Integration @ LondonR/Oct 2010
  • 30. Background API Sugar Modules Overview R side Modules: on the R side R side: based on R 2.12.0 reference classes (see ?ReferenceClasses) > World <- yada$World > w <- new( World ) > w$greet() [1] "hello" > w$set( "hello world") > w$greet() [1] "hello world" > w$clear() > w$greet() [1] "" Dirk Eddelbuettel and Romain François Seamless R anc C++ Integration @ LondonR/Oct 2010
  • 31. Want to learn more ? Check the vignettes Questions on the Rcpp-devel mailing list Hands-on training courses Commercial support Romain François romain@r-enthusiasts.com Dirk Eddelbuettel edd@debian.org