问题
Let say I have an ArrayXXf
(or MatrixXf
) m
. In each iteration of a for loop, I want to fill m
row-wise with a VectorXf
.
Eigen::ArrayXXf m(5, 5);
for (int i = 0; i < 5; i++)
{
Eigen::VectorXf vec(5);
vec << i, i + 1, i + 2, i+3, i+4;
//fill m row wise
// in matlab I will do something like m(i,:) = vec;
// in numpy this will looks like m[i:] = vec;
// that means when i is 0 m looks like
// [ 0 1 2 3 4 5
// - - - - - -
// - - - - - -
// - - - - - -
// - - - - - -]
}
How can I achieve that in Eigen?
回答1:
Use block() function.
#include <iostream>
#include <Eigen/Dense>
using namespace std;
int main()
{
Eigen::ArrayXXf m(5, 5);
for (int i = 0; i < 5; i++) {
Eigen::VectorXf vec(5);
vec << i, i + 1, i + 2, i+3, i+4;
m.block(i, 0, 1, 5) << vec.transpose();
}
std::cout << m << std::endl;
return 0;
}
Output:
0 1 2 3 4
1 2 3 4 5
2 3 4 5 6
3 4 5 6 7
4 5 6 7 8
Edit:
There is one simpler alternative also: row() function.
#include <iostream>
#include <Eigen/Dense>
using namespace std;
int main()
{
Eigen::ArrayXXf m(5, 5);
for (int i = 0; i < 5; i++) {
Eigen::VectorXf vec(5);
vec << i, i + 1, i + 2, i+3, i+4;
m.row(i) = vec.transpose();
}
std::cout << m << std::endl;
return 0;
}
Output:
0 1 2 3 4
1 2 3 4 5
2 3 4 5 6
3 4 5 6 7
4 5 6 7 8
P.S. transpose() is required because Eigen::VectorXf by default is a column vector, not a row vector.
回答2:
To simplify @Kunal's answer, you can directly modify rows (or columns) of an Array (or Matrix) without creating a temporary vector. In your example you can use .setLinSpaced()
:
Eigen::ArrayXXf m(5, 5);
for (int i = 0; i < 5; i++) {
m.row(i).setLinSpaced(i,i+4); //.col(i) would be slightly more efficient
}
or use the comma initializer:
for (int i = 0; i < 5; i++) {
m.row(i) << i, i+1, i+2, i+3, i+4;
}
来源:https://stackoverflow.com/questions/53877801/eigen-indexing-update-all-column-of-a-specific-row