如何将cv :: Mat&Img复制到未签名的char * img?

时间:2018-08-27 02:19:20

标签: c++ opencv

如何将“ Mat&imgSrc”复制到“ unsigned char * imgSrc”?

void BGR2NV21( unsigned char* bgrData, int w, int h, unsigned char* nv21Data)
{.............}

int enhanceRGB( cv::Mat& fieldFaceImgSrc, int iWidth,int iHeight, cv::Mat& faceImgDst)
{
    cv::imwrite("enhanceInput.jpg", fieldFaceImgSrc); //it's ok

    cv::Mat faceBackupData;
    faceBackupData = fieldFaceImgSrc.clone();       //it's ok
    cv::imwrite("enhanceput.jpg", faceBackupData);  //it's ok

    unsigned char*pcfieldFaceDataNV21 = (unsigned char*)faceBackupData .data;

    BGR2NV21(pcfieldFaceDataNV21,                   //it's bad,pcfieldFaceDataNV21  is bad data;
             iWidth, iHeight, pcfieldFaceDataNV21);
}

感谢您的帮助。

3 个答案:

答案 0 :(得分:0)

是否有错误消息或图像只是“错误”?

要检查的两个明显的问题是,您是否正确传递了图像的宽度和高度?相机API(x,y)和图像处理矩阵API(row,col)之间的图像一直是痛苦的源泉

opencv将图像的行填充到32位(4字节边界),请参见Stride on image using Opencv C++

答案 1 :(得分:0)

它可能失败的原因之一是关于渠道的管理。 OpenCV的Mat对象如果不是子矩阵,则连续存储数据。 该存储遵循原始行的顺序,即:

矩阵: | 1 2 3 | | 4 5 6 | | 7 8 9 |

将按以下顺序存储线性指针:1、2、3、4、5、6、7、8、9。

对于通道也是如此,即让两个像素的值分别为[255,64,128]和[64,12,34]对应于坐标row = 0,col = 0和row = 0 col = 1,将连续存储在内存中(data的前六个值分别为255,64,128,64,12,34)

现在将data对象的Mat指针复制到另一个数据指针的最简单方法是:

std::memcpy(dst,src,rows*cols*elemsize);或如果您传递Mat对象:

if(obj.isContiguous())
  std::memcpy(dst,src.ptr(),src.rows*src.step); // if you data are of type unsigned char src.step == src.cols otherwise src.step = src.cols*src.elemSize()
else
   for(int r=0;r<src.rows;r++,dst+=src.step)
      std::memcpy(dst,src.ptr(r),src.step);

答案 2 :(得分:0)

对不起,总是有一些问题,代码是:

int enhanceRGB( cv::Mat fieldFaceImgSrc, int iWidth,int iHeight, cv::Mat& faceImgDst)
{
cv::imwrite("enhanceInput.jpg", fieldFaceImgSrc); //it's ok
    cv::Mat faceBackupData;
    faceBackupData = fieldFaceImgSrc.clone();
    cv::imwrite("enhanceput.jpg", faceBackupData);   //it's ok

    unsigned char *testdata = (unsigned char*)malloc(iWidth * iHeight * 3 * sizeof(unsigned char));
    memcpy(testdata, faceBackupData.ptr(), iWidth * iHeight * 3);
    cv::Mat FaceData(iHeight , iWidth, CV_8UC3, testdata);
    cv::imwrite("testput.jpg", FaceData);           //it's bad
}