消除中间特征阵列

时间:2017-08-13 17:12:05

标签: c++ eigen

Eigen是否为计算x或Eigen制作任何中间数组,只需将这些值放入simd寄存器并进行计算?

一般来说,如何知道Eigen做了多少中间体?

Eigen会在循环的每个循环中为中间体分配新内存吗?

无论如何确保本征不会产生任何中间体?它是否有像#34; EIGEN_NO_INTERMEDIATE"?

#include <Eigen/Eigen>
#include <iostream>

using namespace Eigen;

template<typename T>
void fill(T& x) {
    for (int i = 0; i < x.size(); ++i) x.data()[i] = i + 1;
}

int main() {
    int n = 10;  // n is actually about 400
    ArrayXXf x(n, n);
    ArrayXf y(n);
    fill(x);
    fill(y);
    for (int i = 0; i < 10; ++i) {  // many cycles
        x = x * ((x.colwise() / y).rowwise() / y.transpose()).exp();
    }
    std::cout << x << "\n";
}

1 个答案:

答案 0 :(得分:4)

您可以在DenseStorage构造函数中添加一个钩子,如下所示:

#include <iostream>

static long int nb_temporaries;
inline void on_temporary_creation(long int size) {
  if(size!=0) nb_temporaries++;
}

// must be defined before including any Eigen header!
#define EIGEN_DENSE_STORAGE_CTOR_PLUGIN { on_temporary_creation(size); }

#define VERIFY_EVALUATION_COUNT(XPR,N) {\
    nb_temporaries = 0; \
    XPR; \
    if(nb_temporaries!=N) { std::cerr << "nb_temporaries == " << nb_temporaries << "\n"; }\
  }

#include <Eigen/Core>
using namespace Eigen;

template<typename T>
void fill(T& x) { for(int i=0; i<x.size(); ++i) x(i)= i+1; }

int main() {
    int n=10;
    ArrayXXf x(n,n); fill(x);
    ArrayXf y(n); fill(y);

    for(int i=0; i<10; ++i)
    {
        VERIFY_EVALUATION_COUNT( x = x * ((x.colwise()/y).rowwise()/y.transpose()).exp(), 0);
    }
    std::cout << x << '\n';
}

基本上,这就是Eigen在某些方面在其测试中所做的事情: 请参阅here for the original definition in the testsuitehere for an example usage in the testsuite

或者,如果你只关心中间内存分配,你可以尝试宏EIGEN_RUNTIME_NO_MALLOC - 这将允许固定大小的表达式计算临时值,因为它们只会在栈上分配。

相关问题