Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Rcpp + inline - creating and calling additional functions

Tags:

r

rcpp

I would like to know if there is a way to create Rcpp functions using the inline packages within the main function. This is an example of what I want to do:

library(inline)
library(Rcpp)
a = 1:10
cpp.fun = cxxfunction(signature(data1="numeric"), 
                      plugin="Rcpp",
                      body="
int fun1( int a1)
{int b1 = a1;
 b1 = b1*b1;
 return(b1);
}

NumericVector fun_data  = data1;
int n = data1.size();
for(i=0;i<n;i++){
fun_data[i] = fun1(fun_data[i]);
}
return(fun_data);
                           ")

which should result in:

> cpp.fun(a)
[1]  1  4  9  16  25  36  49  64  81  100

however I know that the compiler will not accept the creation of your own function within the main method. How will I go about creating and calling another Rcpp function with inline without having to pass it through to R?

like image 491
honeyoak Avatar asked Dec 19 '12 16:12

honeyoak


1 Answers

body is for the body of the function, you want to look at the includes argument of cxxfunction:

library(inline)
library(Rcpp)
a = 1:10
cpp.fun = cxxfunction(signature(data1="numeric"), 
                      plugin="Rcpp",
                      body='

IntegerVector fun_data  = data1;
int n = fun_data.size();
for(int i=0;i<n;i++){
    fun_data[i] = fun1(fun_data[i]);
}
return(fun_data);
', includes = '

int fun1( int a1){
    int b1 = a1;
    b1 = b1*b1;
    return(b1);
}

' )    
cpp.fun( a )

?cxxfunction has detailed documentation about its includes argument.

But note that this version will make in place modifications in your input vector, which is probably not what you want. Another version that also takes advantage of Rcpp version of sapply:

library(inline)
library(Rcpp)
a = 1:10
cpp.fun = cxxfunction(signature(data1="numeric"), 
                      plugin="Rcpp",
                      body='

IntegerVector fun_data  = data1; 
IntegerVector out = sapply( fun_data, fun1 ) ;
return(out);
', includes = '

int fun1( int a1){
    int b1 = a1;
    b1 = b1*b1;
    return(b1);
}

' )    
cpp.fun( a )
a

Finally, you definitely should have a look at sourceCpp. With it you would write your code in a .cpp file, containing:

#include <Rcpp.h>
using namespace Rcpp ;

int fun1( int a1){
    int b1 = a1;
    b1 = b1*b1;
    return(b1);
}

// [[Rcpp::export]]
IntegerVector fun(IntegerVector fun_data){ 
    IntegerVector out = sapply( fun_data, fun1 ) ;
    return(out);
}

And then, you can just sourceCpp your file and invoke the function :

sourceCpp( "file.cpp" )
fun( 1:10 )
#  [1]   1   4   9  16  25  36  49  64  81 100
like image 192
Romain Francois Avatar answered Sep 20 '22 13:09

Romain Francois