OpenCV 【一】—— OpenCV中数组指针、图像分块计算、指针取像素值与MatToEigen方法,内存对齐
生活随笔
收集整理的這篇文章主要介紹了
OpenCV 【一】—— OpenCV中数组指针、图像分块计算、指针取像素值与MatToEigen方法,内存对齐
小編覺得挺不錯的,現在分享給大家,幫大家做個參考.
{
Topic1:
高效開辟內存,使適用于大型數組。//開辟新數組,或者開辟新的0或者某一數值的數組/Mat或者Map直接使用memset
//大數組操作效率較高
舉例1:cv::Mat cv_ncc_temp(cv_input_32f.rows, cv_input_32f.cols, CV_8UC1);memset(cv_ncc_temp.data, 0, cv_input_32f.rows*cv_input_32f.cols * sizeof(uint8_t));
舉例2:memset(cv_binary_image.data, 255, cv_input_32f.rows*cv_input_32f.cols / 4);
舉例3:cv::Mat block_flag(max_row, max_col, CV_8UC1);memset(block_flag.data, 0, max_row * max_col * sizeof(uint8_t));//行指針如下
舉例1:*****注意 行指針,整行取出所有元素,列變量便利有兩種方式第一種通過pncc++,指針的方式來操控元素沿著列方向遍歷。for (int i = xy_off; i < cv_input_32f.rows - xy_off; ++i) {uint8_t* psen = cv_ncc_result_temp.ptr<uint8_t>(i);float* pncc = cv_ncc_result.ptr<float>(i - xy_off);for (int j = xy_off; j < cv_input_32f.cols - xy_off; ++j) {*psen = (uint8_t)((*(pncc-xy_off) + 1)*127.5f);pncc++;psen++;}}
等價于:
cv_ncc_result.at<uint8_t>(i,j) = (uint8_t)((cv_ncc_result_temp.at<float>(i-xy_off,j-xy_off))+1)*127.5f舉例2:*****行指針去除整行,列指針通過 *(psen+j)隨著for循環中的j增加而移動,與舉例1中常用的兩種方式。內存溢出情況:主要差一些指針上線,尤其是上限邊緣出,當不規則的分塊或者分類出現時,內存溢出常出現的位置位于此的概率增大。for (int row = 0; row < max_row - 1; ++row) {uint8_t* pblock = block_flag.ptr<uint8_t>(row);for (int col = 0; col < max_col - 1; ++col) {int count = 0;for (int i = row * BLOCK_HEIGHT; i < (row + 1) * BLOCK_HEIGHT; i++) {uint8_t* psen = cv_ncc_result_temp.ptr<uint8_t>(i);for (int j = col * BLOCK_WIDTH; j < (col + 1) * BLOCK_WIDTH; j++) {if ((*(psen + j)) > 165 && (*(psen + j)) < 179) {count++;}}}if (count > 60) {*(pblock + col) = 1;}}}
Topic2:
多指針同時操作,圖像分塊賦值,指針越界問題定位思路
舉例3:*****1)不同for循環中的不同名稱的指針不會相互影響2)*(pblock1 + (j >> 6)等價于block_flag.at<uint8_t>(i/64,j/64) == 0for (int i = 0; i < cv_input_32f.rows; ++i) {uint8_t* pdata = cv_ncc_result_temp.ptr<uint8_t>(i);uint8_t* pblock1 = block_flag.ptr<uint8_t>(i >> 6);///for (int j = 0; j < cv_input_32f.cols; ++j) {if (*(pblock1 + (j >> 6)) == 0)///{if (*(pdata + j) < BACK_GROUND) {(*(pdata + j)) = 0;}}else {if (*(pdata + j) < FORE_GROUND) {(*(pdata + j)) = 0;}}}}Topic3:
Eigen::Map與Mat相互轉換
舉例1:通過指針操作將cv_ncc_result_temp的值賦值給blurred_image,完成Mat到eigen::map的轉換for (int i = xy_off; i < cv_input_32f.rows - xy_off; ++i) {uint8_t* pdata = cv_ncc_result_temp.ptr<uint8_t>(i);for (int j = xy_off; j < cv_input_32f.cols - xy_off; ++j) {uint8_t* pimage = (uint8_t*)(&blurred_image((i + roi[1]), (j + roi[0])));//取指針,以指針元素操作,提高操作效率*pimage = (uint8_t) *(pdata + j);}}
舉例2:通過指針操作完成cv_binary_image到binary_image的賦值,完成Mat到eigen::map的轉換for (int i = 0; i < (int)(roi_rect.height / scale_binary); ++i) {uint8_t* pimage1 = (uint8_t*)(&binary_image(i + roi[1] / scale_binary, roi[0] / scale_binary));memcpy(pimage1, cv_binary_image.ptr<uint8_t>(i), roi_rect.width / scale_binary);}}
注意:
Eigen頭文件要在opencv的eigen.hpp之前,否則報錯!
Eigen中Matrix 與OpenCV中Mat間的轉換
matrix->mat:eigen2cv
vector->mat:eigen2cv
mat->matrix:cv2eigen
mat->vector:cv2eigen?
Matx33d EE;for (int i = 0; i<3; i++)for (int j = 0; j < 3; j++) {//std::cout << "E =" << E.at<double>(i, j) << std::endl;EE(i, j) = E.at<double>(i, j);//std::cout << "E =" << EE(i, j) << std::endl;}std::cout << "EE =" << EE << std::endl;
Eigen與Opencv之間的轉換,在包含Eigen庫的基礎上,#include<opencv2/core/eigen.hpp>
rr = (cv::Mat_<double>(3, 3) << -0.0001, -0.2, 3, 4, 5, 6, 7, 8, 791);
將Eigen::Matrix轉換為cv::Mat
cv::eigen2cv(matrix,mat);
Matx33d EE;for (int i = 0; i<3; i++)for (int j = 0; j < 3; j++) {//std::cout << "E =" << E.at<double>(i, j) << std::endl;EE(i, j) = E.at<double>(i, j);std::cout << "E =" << EE(i, j) << std::endl;}std::cout << "EE =" << EE << std::endl; std::string filename3 = "./debug_output/xEx_output.txt";FILE* fp3 = fopen(filename3.c_str(), "at+");for (int i = 0; i < points1.size(); i++) {Vec3d x1(points1[i].x, points1[i].y, 1.);Vec3d x2(points2[i].x, points2[i].y, 1.);// Matx33d E(model.ptr<double>());// E = cv::eigen2cv(E, ee);// Eigen::Matrix3d er;//cv::cv2eigen(E, er);cv::Mat rr;Eigen::Matrix3d er;// rr = (cv::Mat_<double>(3, 3) << -0.0001, -0.2, 3, 4, 5, 6, 7, 8, 791);// cv::cv2eigen(rr, er); //cv to eigen Matx33d EE(-0.0001, -0.2, 3, 4, 5, 6, 7, 8, 791);Vec3d Ex1 = EE * x1;Vec3d Etx2 = EE.t() * x2;float x2tEx1 = x2.dot(Ex1);fprintf(fp3,"%10.8f\n",x2tEx1);} fclose(fp3);
A::BB(目標類型)cConverter::XXXX(const C::DD(代轉類型) &XXX){……}?
cv::Mat cConverter::toCvMatInverse(const cv::Mat &Tcw){cv::Mat Rcw = Tcw.rowRange(0,3).colRange(0,3);cv::Mat tcw = Tcw.rowRange(0,3).col(3);cv::Mat Rwc = Rcw.t();cv::Mat twc = -Rwc*tcw;cv::Mat Twc = cv::Mat::eye(4,4,Tcw.type());Rwc.copyTo(Twc.rowRange(0,3).colRange(0,3));twc.copyTo(Twc.rowRange(0,3).col(3));return Twc.clone();}cv::Mat cConverter::toCvMat(const Eigen::Matrix<double,3,1> &m){cv::Mat cvMat(3,1,CV_32F);for(int i=0;i<3;i++)cvMat.at<float>(i)=m(i);return cvMat.clone();}cv::Mat cConverter::Matrix3dtoCvMat(const Eigen::Matrix3d &m){cv::Mat cvMat(3,3,CV_32F);for(int i=0;i<3;i++)for(int j=0; j<3; j++)cvMat.at<float>(i,j)=m(i,j);return cvMat.clone();}cv::Mat cConverter::Matx33dtoCvMat(const Eigen::Matrix3d &m){cv::Mat cvMat(3,3,CV_32F);for(int i=0;i<3;i++)for(int j=0; j<3; j++)cvMat.at<float>(i,j)=m(i,j);return cvMat.clone();}cv::Mat cConverter::Matx44dtoCvMat(const Eigen::Matrix<double,4,4> &m){cv::Mat cvMat(4,4,CV_32F);for(int i=0;i<4;i++)for(int j=0; j<4; j++)cvMat.at<float>(i,j)=m(i,j);return cvMat.clone();}Eigen::Matrix<double,3,1> cConverter::toVector3d(const cv::Mat &cvVector){Eigen::Matrix<double,3,1> v;v << cvVector.at<float>(0), cvVector.at<float>(1), cvVector.at<float>(2);return v;}Eigen::Matrix<double,3,3> cConverter::toMatrix3d(const cv::Mat &cvMat3){Eigen::Matrix<double,3,3> M;M << cvMat3.at<float>(0,0), cvMat3.at<float>(0,1), cvMat3.at<float>(0,2),cvMat3.at<float>(1,0), cvMat3.at<float>(1,1), cvMat3.at<float>(1,2),cvMat3.at<float>(2,0), cvMat3.at<float>(2,1), cvMat3.at<float>(2,2);return M;}//+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++cv::Matx44d cConverter::invMat(const cv::Matx44d& M){cv::Matx33d R = M.get_minor<3, 3>(0, 0);R = R.t();cv::Vec3d t(M(0, 3), M(1, 3), M(2, 3));t = -R * t;cv::Matx44d out(R(0, 0), R(0, 1), R(0, 2), t(0),R(1, 0), R(1, 1), R(1, 2), t(1),R(2, 0), R(2, 1), R(2, 2), t(2),0.0, 0.0, 0.0, 1.0);return out;}cv::Matx<double, 4, 4> cConverter::ogv2ocv(const Eigen::Matrix<double, 3, 4>& ogv_mat){cv::Matx34d ocv_mat;cv::eigen2cv(ogv_mat, ocv_mat);return cv::Matx<double, 4, 4>(ocv_mat(0, 0), ocv_mat(0, 1), ocv_mat(0, 2), ocv_mat(0, 3),ocv_mat(1, 0), ocv_mat(1, 1), ocv_mat(1, 2), ocv_mat(1, 3),ocv_mat(2, 0), ocv_mat(2, 1), ocv_mat(2, 2), ocv_mat(2, 3),0.0, 0.0, 0.0, 1.0);}g2o::SE3Quat cConverter::toSE3Quat(const cv::Matx44d& homCV){Eigen::Matrix<double, 3, 3> R;R << homCV(0, 0), homCV(0, 1), homCV(0, 2),homCV(1, 0), homCV(1, 1), homCV(1, 2),homCV(2, 0), homCV(2, 1), homCV(2, 2);Eigen::Matrix<double, 3, 1> t(homCV(0, 3), homCV(1, 3), homCV(2, 3));return g2o::SE3Quat(R, t);}cv::Matx44d cConverter::toCvMat(const g2o::SE3Quat& SE3){Eigen::Matrix<double, 4, 4> eigMat = SE3.to_homogeneous_matrix();return toCvMat(eigMat);}cv::Matx44d cConverter::toCvMat(const g2o::Sim3& Sim3){Eigen::Matrix3d eigR = Sim3.rotation().toRotationMatrix();Eigen::Vector3d eigt = Sim3.translation();double s = Sim3.scale();return toCvSE3(s*eigR, eigt);}cv::Matx44d cConverter::toCvMat(const Eigen::Matrix<double, 4, 4>& m){cv::Matx44d cvMat = cv::Matx44d::eye();cv::eigen2cv(m, cvMat);return cvMat;}cv::Matx33d cConverter::toCvMat(const Eigen::Matrix3d& m){cv::Matx33d cvMat = cv::Matx33d::eye();cv::eigen2cv(m, cvMat);return cvMat;}cv::Matx44d cConverter::toCvSE3(const Eigen::Matrix<double, 3, 3>& R,const Eigen::Matrix<double, 3, 1> &t){cv::Matx44d cvMat = cv::Matx44d::eye();for (int i = 0; i < 3; ++i)for (int j = 0; j < 3; ++j)cvMat(i, j) = R(i, j);for (int i = 0; i < 3; ++i)cvMat(i, 3) = t(i);return cvMat;}Eigen::Matrix<double, 3, 1> cConverter::toVector3d(const cv::Vec4d& cvVector){Eigen::Matrix<double, 3, 1> v;v << cvVector(0), cvVector(1), cvVector(2);return v;}Eigen::Matrix<double, 3, 1> cConverter::toVector3d(const cv::Vec3d& cvVector){Eigen::Matrix<double, 3, 1> v;v << cvVector(0), cvVector(1), cvVector(2);return v;}Eigen::Matrix<double, 3, 3> cConverter::toMatrix3d(const cv::Matx33d& cvMat3){Eigen::Matrix<double, 3, 3> M;M << cvMat3(0, 0), cvMat3(0, 1), cvMat3(0, 2),cvMat3(1, 0), cvMat3(1, 1), cvMat3(1, 2),cvMat3(2, 0), cvMat3(2, 1), cvMat3(2, 2);return M;}cv::Mat cConverter::toMat(const cv::Matx44d& matx44d){cv::Mat out = cv::Mat::zeros(4, 4, CV_64FC1);for (int c = 0; c < 4; ++c)for (int r = 0; r < 4; ++r)out.ptr<double>(r)[c] = matx44d(r, c);return out;}
?
參考網址:
https://blog.csdn.net/u011722133/article/details/80118330
https://blog.csdn.net/piaoxuezhong/article/details/79110421
https://blog.csdn.net/u012706484/article/details/78775360
總結
以上是生活随笔為你收集整理的OpenCV 【一】—— OpenCV中数组指针、图像分块计算、指针取像素值与MatToEigen方法,内存对齐的全部內容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: 我的世界2022年真人电影主角史蒂夫的扮
- 下一篇: CMakeLists.txt学习记录