我有一个Mat2d矩阵,其中每个元素都是一个2D矢量。例如:
[[x0, y0], [x1, y1]
[x2, y2], [x3, y3]]
我想通过Mat1d相机矩阵将每个向量相乘:
[fx, 0, cx,
0, fy, cy,
0, 0, 1]
(每个向量表示网格中顶点的位置,我想将其从相机空间转换为像素空间。)
对于此示例,结果矩阵将是:
[[x0 * fx + cx, y0 * fy + cy], [x1 * fx + cx, y1 * fy + cy]
[x2 * fx + cx, y2 * fy + cy], [x3 * fx + cx, y3 * fy + cy]]
实现这一目标的最简单有效的方法是什么?
这是我目前的做法:
Mat2d points = getMesh();
Mat1d cameraMtrx = getCameraMtrx();
for(int col = 0; col < points.cols; col++){
for(int row = 0; row < points.rows; row++){
points.at<Vec2d>(row, col).val[0] = points.at<Vec2d>(row, col)[0] * cameraMtrx.at<double>(0, 0) + cameraMtrx.at<double>(0, 2);
points.at<Vec2d>(row, col).val[1] = points.at<Vec2d>(row, col)[1] * cameraMtrx.at<double>(1, 1) + cameraMtrx.at<double>(1, 2);
}
}
答案 0 :(得分:2)
OpenCV Documentation已经详细介绍了各种有效迭代cv::Mat
的方法,在提出的方法中,最有效的方法是使用cv::LUT()
,但是从这个问题的上下文中,我猜输入矩阵值的范围不固定,因此无法创建查找表。对于RGB
图像,这非常有用,因为我们事先知道最小值将是0
和最大值将是255
,因此我们可以轻松创建一个lookUp表,但是在这个问题中,我们需要将两个矩阵相乘,我假设它们不是图像,所以我们将使用{{3 }}
int cameraMatrix[] = {2, 0, 10, 0, 4, 20, 0, 0, 1};
cv::Mat mat(2, 2, CV_32FC2, cv::Scalar(100, 20));
cv::Size contSize = mat.size();
// Calculate the length of array if the input matrix was flatten, in case of continuous matrix only.
if (mat.isContinuous()) {
contSize.width *= contSize.height;
contSize.height = 1;
}
cv::Vec2f* ptr;
for (int i = 0; i < contSize.height; ++i)
{
ptr = mat.ptr<cv::Vec2f>(i);
for (int j = 0; j < contSize.width; ++j)
{
ptr[j] = cv::Vec2f(ptr[j].val[0]*cameraMatrix[0] + cameraMatrix[2], ptr[j].val[1] * cameraMatrix[4] + cameraMatrix[5]);
}
}