0

I'm trying to understand why calling arma::pinv of Armadillo takes significantly more time when called in c++ directly (Visual Studio) compared to the same function being called in R via RcppArmadillo.

In R I just followed a super basic approach when compiling/generating the package

MyPackageName <- "thetestpackage"
RcppArmadillo.package.skeleton(MyPackageName, example_code = FALSE)
compileAttributes(pkgdir = paste0("./",MyPackageName), verbose = TRUE)
install(MyPackageName)

In VisualStudio I installed "armadillo-code" and "OpenBLAS" with the NuGet Package manager but I also tried to download Armadillo and include the library with "Additional Include Directories": same results.

My feeling is that I'm not efficiently using LAPACK and/or BLAS. Do you have any ideas? Thanks a lot in advance!

The c++ code run in VS is as follows and takes about 25 sec to run with i = 1000 (iterations) and n = 100 (size of matrix)

#include <iostream>
#include <armadillo>
#include <chrono>  


arma::mat rcpparma_myfun(int i, int n) {
    arma::mat A(n, n);
    A.randn();
    arma::mat B;
    B = arma::pinv(A);
    auto start = std::chrono::high_resolution_clock::now();
    for (int ii = 0; ii < i; ii++) {
        B = arma::pinv(A);
    }
    auto finish = std::chrono::high_resolution_clock::now();
    std::chrono::duration<double> elapsed = finish - start;
    std::cout << "Elapsed time: " << elapsed.count() << " s\n";
    return B;
}

int main()
{
    int iters;
    int size;
    std::cout << "Enter iteration\n";
    std::cin >> iters;
    std::cout << "Enter size\n";
    std::cin >> size;
    arma::mat BB;
    BB = rcpparma_myfun(iters, size);
}

and the cpp function used for RccpArmadillo is as below and takes about 8 sec to run with i = 1000 (iterations) and n = 100 (size of matrix):

#include "RcppArmadillo.h"
// [[Rcpp::depends(RcppArmadillo)]]
// [[Rcpp::export]]
arma::mat rcpparma_myfun(int i, int n) {
    arma::mat A(n,n);
    A.randn();
    arma::mat B;
    B = arma::pinv(A);
    
    for (int ii = 0; ii < i; ii++) {
        B = arma::pinv(A);
    }
    return B;
}
``
horos
  • 1
  • Make sure you link with OpenBLAS instead of the standard (unoptimized) implementations of BLAS and LAPACK. The latest version of OpenBLAS is here: https://github.com/xianyi/OpenBLAS/releases – hbrerkere Oct 13 '20 at 08:39
  • Thanks a lot! So this means when I install OpenBlas with the NuGet Package manager it is not the best way, right? Hence, I will try to install it following these instructions here: https://github.com/xianyi/OpenBLAS/wiki/How-to-use-OpenBLAS-in-Microsoft-Visual-Studio – horos Oct 14 '20 at 18:54
  • It's hard to say if installing using NuGet "is the best way or not" without checking how NuGet compiles and installs openblas, including which compilation flags it uses. Are you sure at least NuGet is compiling with optimizations and not in debug mode? – darcamo Oct 31 '20 at 18:32

0 Answers0