Optimiser le code R avec Rcpp
Romain François
Consulting Datactive, ThinkR
evalCpp("40 + 2")
42
evalCpp("PI")
3.141593
evalCpp("exp(1)")
2.718282
Définir une fonction C++ avec cppFunction()
library(Rcpp)
cppFunction("int fun(){
int x = 37 ;
return x ;
}" )
Appeler cette fonction depuis R
fun()
37
cppFunction("int fun(){
int x = 37 ;
return x ;
}", verbose = TRUE )
Code généré pour la définition de la fonction :
------------------------------------------------------
#include <Rcpp.h>
using namespace Rcpp;
// [[Rcpp::export]]
int fun(){
int x = 37 ;
return x ;
}
Fonctions externes "C" générées
-----------------------------------------------------
#include <Rcpp.h>
// fun
int fun();
RcppExport SEXP sourceCpp_1_fun() {
BEGIN_RCPP
Rcpp::RObject rcpp_result_gen;
Rcpp::RNGScope rcpp_rngScope_gen;
rcpp_result_gen = Rcpp::wrap(fun());
return rcpp_result_gen;
END_RCPP
}
Fonctions R générées
-----------------------------------------------
`.sourceCpp_1_DLLInfo` <- dyn.load('/private/var/folders/r_/1b2gjtsd7j92jbbpz4t7ps340000gn/T
/Rtmpl8dL6H/sourceCpp-x86_64-apple-darwin15.6.0-0.12.16/sourcecpp_4bb22c766031/sourceCpp_2.so')
fun <- Rcpp:::sourceCppFunction(function() {}, FALSE, `.sourceCpp_1_DLLInfo`, 'sourceCpp_1_fun')
rm(`.sourceCpp_1_DLLInfo`)
Création de la bibliothèque partagée
----------------------------------------------------
DIR: /private/var/folders/r_/1b2gjtsd7j92jbbpz4t7ps340000gn/T/Rtmpl8dL6H/sourceCpp-x86_64-
apple-darwin15.6.0-0.12.16/sourcecpp_4bb22c766031
/Library/Frameworks/R.framework/Resources/bin/R CMD SHLIB -o 'sourceCpp_2.so' 'file4bb247d077c.cpp'
clang++ -I/Library/Frameworks
/R.framework/Resources/include -DNDEBUG -I"/Library/Frameworks/R.framework/Versions/3.4/
Resources/library/Rcpp/include" -I"/private/var/folders/r_/1b2gjtsd7j92jbbpz4t7ps340000gn/
T/Rtmpl8dL6H/sourceCpp-x86_64-apple-darwin15.6.0-0.12.16" -I/usr/local/include -fPIC
-Wno-unused-result -Wno-c++11-inline
-namespace -O3 -c file4bb247d077c.cpp -o file4bb247d077c.o
clang++ -dynamiclib -Wl,-headerpad_max_install_names -undefined dynamic_lookup -single_module
-multiply_defined suppress -L/Library/Frameworks/R.framework/Resources/lib -L/usr/local/lib
-o sourceCpp_2.so file4bb247d077c.o -F/Library/Frameworks/R.framework/.. -framework R -Wl,-framework
-Wl,CoreFoundation
Définir une fonction C++ avec cppFunction()
library(Rcpp)
cppFunction("int fun(){
int x = 37 ;
return x ;
}" )
Appeler cette fonction depuis R.
fun()
37
R est à typage dynamique
x <- "hello"
x
typeof(x)
"hello""character"
x <- 42L
x
typeof(x)
42"integer"
C++ est à typage statique.
// Déclarer x comme double
double x = 42.0 ;
// Impossible de le redéclarer comme int
// ----> cela ne compilerait pas
int x = 14 ;
types des arguments x et y : double
| |
v v
double add( double x, double y ){
// corps de la fonction
// ...
}
type de retour : double
|
v
double add( double x, double y ){
// corps de la fonction
// ...
// ...
}
type de retour : double
|
| nom de la fonction : add
| |
| | types des arguments x et y : double
| | | |
v v v v
double add( double x, double y ){
// corps de la fonction
// ...
// ...
}
Fonction C++ pour additionner deux double.
cppFunction( "
double add( double x, double y){
double res = x + y ;
return res ;}
" )
add( 30, 12 )
Équivalent en R
addr <- function(x, y) {
res <- x + y
res}
Optimiser le code R avec Rcpp