Как написать шаблонную версию этого кода Eigen? - PullRequest
0 голосов
/ 30 января 2019

Это ломтики MatrixXd с Array<bool, Dynamic, 1>, так же, как в Matlab вы можете сделать A(A>5), здесь вы можете сделать slice(A, A.array() > 5).Я хотел бы превратить это в шаблонную версию, чтобы она могла принимать любой тип матриц или векторов, например Matrix3i или VectorXi.Эта страница говорит мне использовать MatrixBase<Derived>, но я не смог продвинуться далеко.ИДК, как объявить шаблонную матрицу определенного размера.https://eigen.tuxfamily.org/dox/TopicFunctionTakingEigenTypes.html

#include <Eigen/Dense>
using namespace Eigen;

MatrixXd slice(const MatrixXd & mat, const Array<bool, Dynamic, 1> & ind)
{
    assert(mat.cols() == ind.size());
    // find out dimensions of the matrix going out
    int _cols = 0;
    for(int i = 0; i < ind.size(); ++i)
    {
        if(ind[i] == 1)
        {
            _cols += 1;
        }
    }
    //populate the matrix going out, in a column major way
    int _pos = 0;
    MatrixXd out = MatrixXd::Zero(mat.rows(), _cols);
    for(int i = 0; i < ind.size(); ++i)
    {
        if(ind[i] == 1)
        {
            out.col(_pos) = mat.col(i);
            _pos += 1;
        }
    }
    return out;
}

И использование такое:

MatrixXd A(4, 4);
A << 1,2,3,4,
     5,6,7,8,
     1,5,6,3,
     9,8,6,5;
VectorXd b(4);
b << 23,-4,1234,3;
cout << A << endl;
cout << (b.array() > 5) << endl;
cout << slice(A, b.array() > 5) << endl;

Вывод такой:

1 2 3 4
5 6 7 8
1 5 6 3
9 8 6 5
1
0
1
0
1 3
5 7
1 6
9 6

Буду признателен, если кто-нибудь покажет мнекак это сделать!

PS: Кажется, в документах есть похожая функциональность: https://eigen.tuxfamily.org/dox-devel/group__TutorialSlicingIndexing.html Но мне буквально не удалось найти ключевое слово all в Eigen / Core, как

std::vector<int> ind{4,2,5,5,3};
MatrixXi A = MatrixXi::Random(4,6);
cout << "Initial matrix A:\n" << A << "\n\n";
cout << "A(all,ind):\n" << A(all,ind) << "\n\n";

И моя IDE тоже не может ее решить.

...