blitz++ is a C library for high dimensional maths.
Need to add explanation here:
library(Rcpp)
library(inline)
## Loading required package: methods
inc = '
#include <blitz/array.h>
'
src = '
using namespace blitz;
Rcpp::NumericVector A(A_);
Rcpp::NumericVector A2(A2_);
// read dimension attribute of R arrays
Rcpp::IntegerVector d1 = A.attr("dim");
Rcpp::IntegerVector d2 = A2.attr("dim");
// create 2 blitz cubes B and B2
// supply contents of dim vectors manually
blitz::Array<double,3> B(A.begin(), shape(d1(0),d1(1),d1(2)), neverDeleteData);
blitz::Array<double,3> B2(A2.begin(), shape(d2(0),d2(1),d2(2)), neverDeleteData);
// do some blitz arithmethic
blitz::Array<double,3> C(d1(0),d1(1),d1(2));
C = B + B2;
// copy the result back to B (which is a view of A, i.e. will contain the same data)
B = C;
// return array
return wrap(A);
'
Result:
A = array(1:60,c(2,5,6))
A2 = array(120:60,c(2,5,6))
f = cxxfunction(signature(A_="numeric",A2_="numeric"),body=src,plugin="Rcpp",includes=inc)
## Warning: running command '/Library/Frameworks/R.framework/Resources/bin/R
## CMD SHLIB file58337ad31da0.cpp 2> file58337ad31da0.cpp.err.txt' had status
## 1
## clang: warning: argument unused during compilation: '-rdynamic'
## In file included from file58337ad31da0.cpp:4:
## In file included from /Library/Frameworks/R.framework/Versions/2.15/Resources/library/Rcpp/include/Rcpp.h:27:
## /Library/Frameworks/R.framework/Versions/2.15/Resources/library/Rcpp/include/RcppCommon.h:145:10: fatal error: 'tr1/unordered_map' file not found
## #include <tr1/unordered_map>
## ^
## 1 error generated.
## make: *** [file58337ad31da0.o] Error 1
##
## ERROR(s) during compilation: source code errors or compiler configuration errors!
##
## Program source:
## 1:
## 2: // includes from the plugin
## 3:
## 4: #include <Rcpp.h>
## 5:
## 6:
## 7: #ifndef BEGIN_RCPP
## 8: #define BEGIN_RCPP
## 9: #endif
## 10:
## 11: #ifndef END_RCPP
## 12: #define END_RCPP
## 13: #endif
## 14:
## 15: using namespace Rcpp;
## 16:
## 17:
## 18: // user includes
## 19:
## 20: #include <blitz/array.h>
## 21:
## 22:
## 23: // declarations
## 24: extern "C" {
## 25: SEXP file58337ad31da0( SEXP A_, SEXP A2_) ;
## 26: }
## 27:
## 28: // definition
## 29:
## 30: SEXP file58337ad31da0( SEXP A_, SEXP A2_ ){
## 31: BEGIN_RCPP
## 32:
## 33: using namespace blitz;
## 34: Rcpp::NumericVector A(A_);
## 35: Rcpp::NumericVector A2(A2_);
## 36:
## 37: // read dimension attribute of R arrays
## 38: Rcpp::IntegerVector d1 = A.attr("dim");
## 39: Rcpp::IntegerVector d2 = A2.attr("dim");
## 40:
## 41: // create 2 blitz cubes B and B2
## 42: // supply contents of dim vectors manually
## 43: blitz::Array<double,3> B(A.begin(), shape(d1(0),d1(1),d1(2)), neverDeleteData);
## 44: blitz::Array<double,3> B2(A2.begin(), shape(d2(0),d2(1),d2(2)), neverDeleteData);
## 45:
## 46: // do some blitz arithmethic
## 47: blitz::Array<double,3> C(d1(0),d1(1),d1(2));
## 48: C = B + B2;
## 49:
## 50: // copy the result back to B (which is a view of A, i.e. will contain the same data)
## 51: B = C;
## 52:
## 53: // return array
## 54: return wrap(A);
## 55:
## 56: END_RCPP
## 57: }
## 58:
## 59:
## Error: Compilation ERROR, function(s)/method(s) not created! clang:
## warning: argument unused during compilation: '-rdynamic' In file included
## from file58337ad31da0.cpp:4: In file included from
## /Library/Frameworks/R.framework/Versions/2.15/Resources/library/Rcpp/include/Rcpp.h:27:
## /Library/Frameworks/R.framework/Versions/2.15/Resources/library/Rcpp/include/RcppCommon.h:145:10:
## fatal error: 'tr1/unordered_map' file not found #include
## <tr1/unordered_map> ^ 1 error generated. make: *** [file58337ad31da0.o]
## Error 1
all.equal(f(A,A2),A+A2)
## Error: could not find function "f"
======================================================== Using the RcppArmadillo library ========================================================
The Armadillo C++ library provides vector, matrix and cube types. We convert an R array to a cube in RcppArmadillo.
First in the "arma.cpp" file
// [[Rcpp::depends(RcppArmadillo)]]
#include <RcppArmadillo.h>
using namespace Rcpp;
// [[Rcpp::export]]
SEXP f(SEXP A_, SEXP A2_){
NumericVector A(A_);
NumericVector A2(A2_);
// read dimension attribute of R arrays
IntegerVector d1 = A.attr("dim");
IntegerVector d2 = A2.attr("dim");
// create 2 cubes B and B2
// supply contents of dim vectors manually
arma::cube B(A.begin(), d1[0], d1[1], d1[2], false);
arma::cube B2(A2.begin(), d2[0], d2[1], d2[2], false);
// do some arithmethic
arma::cube C(d1[0], d1[1], d1[2]);
C = B + B2;
// copy the result back to B (which is a view of A, i.e. will contain the same data)
B = C;
// return array
return wrap(A);
}
Then in the "arma.r" file
require(Rcpp)
require(RcppArmadillo)
sourceCpp("arma.cpp")
A = array(1:60,c(2,5,6))
A2 = array(120:60,c(2,5,6))
all.equal(f(A,A2),A+A2)