Hi,

Following up on http://news.gmane.org/gmane.comp.lang.r.rcpp
I've commited quite a bit of code today.

The idea of sugar really is to bring a subset of the R syntax right into C++.

First I had to change a few implementation details of the Vector class so that one of its base class implements CRTP: http://en.wikipedia.org/wiki/Curiously_recurring_template_pattern

Then, I made the previously advertised functions any, all, etc ... more generic through the base template class VectorBase.

Then, I added some more syntax. Currently sugar has the functions:

any, all, is_na, seq_along, seq_len

and knows about the operators <,>,<=,>=,!=,==,+



Here are a few selected examples (from the unit test suite):

test.sugar.plus <- function( ){

        fx <- cxxfunction( signature( x = "integer" ), '
                IntegerVector xx(x) ;
                return List::create(
                        xx + 10,
                        10 + xx,
                        xx + xx
                        ) ;
        ', plugin = "Rcpp" )
        
        checkEquals( fx(1:10) , list( 11:20,11:20,1:10+1:10)  )
}

We start of with

IntegerVector xx(x) ;

which should be familiar to people using the Rcpp API... nothing new here.

Then the expressions "xx + 10", "10 + xx", and "xx + xx" are new things. They do what you would do in R like this:

> x <- 1:10
> x + 10
 [1] 11 12 13 14 15 16 17 18 19 20
> 10 + x
 [1] 11 12 13 14 15 16 17 18 19 20
> x + x
 [1]  2  4  6  8 10 12 14 16 18 20

The big difference is that, unlike R, Rcpp sugar expressions are managed at compile time, thanks to the technique of expression templates (see also Armadillo or Blitz++).


Another example:

        fx <- cxxfunction( signature( x = "numeric" ), '
                NumericVector xx(x) ;
                return all( xx <= 5.0 ) ;
        
        ', plugin = "Rcpp" )
        
        fx( c(1:1000000) )

Here, R would first allocate a logical vector to store the result of "xx <= 5.0" (a logical vector of size 1000000) and then apply "all".

The "all" function in Rcpp is lazy, so it does not allocate the vector, and only has to do 6 comparisons (1,2,3,4,5,6) to decide that the result is FALSE.


sugar expressions can be combined, so for example this works:

test.sugar.plus.all <- function( ){

        fx <- cxxfunction( signature( x = "integer" ), '
                IntegerVector xx(x) ;
                return all( (xx+xx) < 10 ) ;
        ', plugin = "Rcpp" )
        
        checkEquals( fx(1:10) , FALSE )
}


There is still much work to be done (see the TODO file), but I think this has quite some potential.

Romain

--
Romain Francois
Professional R Enthusiast
+33(0) 6 28 91 30 30
http://romainfrancois.blog.free.fr
|- http://bit.ly/98Uf7u : Rcpp 0.8.1
|- http://bit.ly/c6YnCi : graph gallery collage
`- http://bit.ly/bZ7ltC : inline 0.3.5

_______________________________________________
Rcpp-devel mailing list
[email protected]
https://lists.r-forge.r-project.org/cgi-bin/mailman/listinfo/rcpp-devel

Reply via email to