Armadillo медленнее, чем RcppArmadillo

#c #armadillo #openblas #rcpparmadillo

#c #armadillo #openblas #rcpparmadillo

Вопрос:

Я пытаюсь понять, почему вызов arma::pinv Armadillo занимает значительно больше времени при вызове в c напрямую (Visual Studio) по сравнению с той же функцией, вызываемой в R через RcppArmadillo.

В R я просто следовал супер базовому подходу при компиляции / генерации пакета

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

В VisualStudio я установил «armadillo-code» и «OpenBLAS» с помощью менеджера пакетов NuGet, но я также попытался загрузить Armadillo и включить библиотеку с «Дополнительными каталогами включения»: те же результаты.

У меня такое чувство, что я неэффективно использую LAPACK и / или BLAS. У вас есть какие-нибудь идеи? Заранее большое спасибо!

Код c , выполняемый в VS, выглядит следующим образом и занимает около 25 секунд для выполнения с i = 1000 (итерации) и n = 100 (размер матрицы)

 #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() << " sn";
    return B;
}

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

и функция cpp, используемая для RccpArmadillo, выглядит так, как показано ниже, и для ее выполнения требуется около 8 секунд с i = 1000 (итерации) и n = 100 (размер матрицы):

 #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;
}
``
  

Комментарии:

1. Убедитесь, что вы используете OpenBLAS вместо стандартных (неоптимизированных) реализаций BLAS и LAPACK. Последняя версия OpenBLAS находится здесь: github.com/xianyi/OpenBLAS/releases

2. Большое спасибо! Итак, это означает, что когда я устанавливаю OpenBLAS с помощью менеджера пакетов NuGet, это не лучший способ, верно? Следовательно, я попытаюсь установить его, следуя этим инструкциям здесь: github.com/xianyi/OpenBLAS/wiki /…

3. Трудно сказать, является ли установка с использованием NuGet «лучшим способом или нет», не проверив, как NuGet компилирует и устанавливает openblas, в том числе какие флаги компиляции он использует. Вы уверены, что по крайней мере NuGet компилируется с оптимизацией, а не в режиме отладки?