Построить матрицу из меньших матриц / векторов - PullRequest
0 голосов
/ 27 мая 2019

Моя окончательная матрица A должна иметь размер mxm, где у меня есть два вектора v , k , которые имеют размер (m-1) и должны быть первым столбцом и строкой соответственно в A , исключая элемент в (0, 0), который равен 1. Остальные элементы A соответствуют некоторой матрице M размера (м-1) х (м-1).

Пример для матрицы 3 x 3

Для следующих компонентов

 v = 2 2
 k = 3 3

 M = 4 4
     4 4

Я бы хотел получить

A = 1 2 2
    3 4 4
    3 4 4

Примечание: Элементы v, k и M в действительности могут быть произвольными.

код

Мой код выглядит следующим образом для примера матрицы размером 3 x 3.

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

int main(){

  Eigen::MatrixXd m;
  m.resize(3,3);

  Eigen::VectorXd v;
  v.resize(3);
  v[0] = 1 ;
  v[1] = 2;
  v[2] = 2;

  Eigen::VectorXd k;
  k.resize(3);
  k[0] = 1;
  k[1] = 3;
  k[2] = 3;

  Eigen::Matrix2d a = Eigen::Matrix2d::Constant(4);

  m.col(0) = k;
  m.row(0) = v;
  m.block<2,2>(1,1) = a;

  std::cout << m << std::endl;
  return 0;
}

Вывод выглядит следующим образом:

1 2 2
3 4 4
3 4 4

В реальной программе конечная матрица будет порядка 10 ^ 4 - 10 ^ 6. Поскольку я довольно новичок в C ++, мне было интересно, если это будет наиболее эффективным и элегантным, чтобы сделать это, и если у меня могут возникнуть проблемы, когда дело доходит до больших матриц?

1 Ответ

1 голос
/ 27 мая 2019

Предполагая, что v и k являются n x 1 векторами, а M является n x n матрицей, вы можете написать:

Eigen::MatrixXd A(M.rows()+1, M.cols()+1);
A << 1, v.transpose(),
     k, M;

Это почти то же самое, что и ваш код с использованием row, col и block, но, вероятно, более читабельно. И если это не произойдет внутри критического цикла, я бы не стал сильно беспокоиться о производительности здесь.

Если это происходит внутри критического цикла, рассмотрите возможность сохранения только A и доступа к M, v и k по некоторому блочному выражению.

...