I'm trying to use R within C++ via RInside. I'm having trouble passing armadillo matrices to R and returning a result. Below I am able to return a results from an R library function, however I get the wrong result. I'm using the skewness function from the moments package as an example which works as should in R. I checked the examples from RInside and i'm still unsure how to use RcppArmadillo. How do I properly pass an armadillo matrix in c++ to R?
#include <RInside.h>
#include <RcppArmadillo.h>
using namespace std;
using namespace arma;
int main(int argc, char *argv[]) {
RInside R(argc, argv);
string R_libs = "suppressMessages(library(moments));";
R.parseEvalQ(R_libs);
mat A = randu<mat>(5,5);
R["A"] = A;
string R_skewness = "B <- skewness(A);";
//this fails
mat B = Rcpp::as<mat>(R.parseEval(R_skewness)); //terminate called after throwing an instance of 'Rcpp::not_a_matrix'
//this works but wrong
mat B = Rcpp::as<vec>(R.parseEval(R_skewness)); // returns only 1 number, should be 5 ( 1 for each columnn), same result if i change mat B to vec B
exit(0);
}
The way we implemented as<mat>
requires that the R object you pass is a matrix. And in your example B
is a vector:
> A <- matrix( runif(25), ncol = 5)
> A
[,1] [,2] [,3] [,4] [,5]
[1,] 0.19215339 0.5857249 0.14345222 0.32154176 0.6162155
[2,] 0.95753898 0.9618379 0.06239842 0.06200197 0.7044018
[3,] 0.33575790 0.1372804 0.03027635 0.62662467 0.9778451
[4,] 0.16504957 0.1919765 0.49176372 0.94841456 0.2914772
[5,] 0.01570709 0.8055231 0.51218581 0.79562809 0.6939380
> B <- skewness( A )
> B
[1] 1.15196587 -0.04547576 0.32186257 -0.30788111 -0.29251009
For conversion to arma::vec
I don't reproduce the behavior you see. The arma::vec
has 3 elements:
require( RcppArmadillo ) ## and make sure you have Rcpp 0.10.0 or later
sourceCpp( code = '
// [[Rcpp::depends("RcppArmadillo")]]
#include <RcppArmadillo.h>
using namespace arma ;
using namespace Rcpp ;
// [[Rcpp::export]]
List foo( NumericVector x){
vec B = Rcpp::as<vec>(x);
return List::create(
_["nrows"] = B.n_rows,
_["ncols"] = B.n_cols
) ;
}
')
foo( c(1, 2, 3 ) )
# $nrows
# [1] 3
#
# $ncols
# [1] 1
You are trying compound expression involving several heavily templated libraries. That can go wrong. I;d recommended to do it in pieces:
Make sure you have the matrix A
you expect passed down to the embedded R
Make sure the function calls worked right, check the result.
Important: check the result type. A matrix should come back fine.
Get the result back to C++.
Get it to Rcpp.
Use RcppArmadillo marshaling to get to Armadillo.
In principle, this should work. The devil is in the detail, as always.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With