您的位置:首页 > 运维架构

OpenCV处理像素值

2013-11-14 16:43 169 查看


OpenCV对像素值的获取及赋值1 OpenCV中像素值的获取    Opencv 获取像素值主要有两种方式:
1.1 CvScalar     OpenCV中,CvScalar结构为:
    typedef struct CvScalar
    {
        double val[4];
    }
    CvScalar;    CvScalar s;    s=cvGet2D(img,i,j); //img就是IplImage指针    如果图像是单通道的话就是只有s.val[0]有像素值如果是3通道的就s.val[0]s.val[1]s.val[2]分别对应了像素的B G R1.2 imageData     mg->imageData 就是指向像素数据的指针2 OpenCV中像素的赋值    cvSet2D 给某个点赋值。
    cvSet2D定义:CVAPI(void) cvSet2D( CvArr* arr, int idx0, int idx1, CvScalar value );
【示例】    #include <highgui.h>    #include <iostream>    using namespace std;    int main()    {        IplImage* src = cvLoadImage("e:/11.bmp",CV_LOAD_IMAGE_COLOR);        //方法一:        CvScalar s = cvGet2D(src,200,201);//获取像素点为(201,200)点的BGR的值         //注:此处的x,y值是反的,具体不解释        cout<<s.val[0]<<'\t'<<s.val[1]<<'\t'<<s.val[2]<<endl;//输出B值,G值,R值        //方法二:此处输出的时候进行强制类型转换就可以得到和上面一样的值。不能直接输出uchar?
        //坐标(200,201)的像素值        cout<<(int)((uchar*)(src->imageData+200*src->widthStep))[3*201]<<endl;        cout<<(int)((uchar*)(src->imageData+200*src->widthStep))[3*201+1]<<endl;        cout<<(int)((uchar*)(src->imageData+200*src->widthStep))[3*201+1]<<endl;
        cvReleaseImage(&src);        return 0;    }

附:
IplImage
|-- int  nChannels;     // 颜色通道数目 (1,2,3,4)
|-- int  depth;         // 像素的位深:
|                       //   IPL_DEPTH_8U, IPL_DEPTH_8S,
|                       //   IPL_DEPTH_16U,IPL_DEPTH_16S,
|                       //   IPL_DEPTH_32S,IPL_DEPTH_32F,
|                       //   IPL_DEPTH_64F
|-- int  width;         // 图像宽度(像素为单位)
|-- int  height;        // 图像高度
|-- char* imageData;    // 图像数据指针
|                       // 注意彩色图像按BGR顺序存储数据
|-- int  dataOrder;     // 0 - 将像素点不同通道的值交错排在一起,形成单一像素平面
|                       // 1 - 把所有像素同通道值排在一起,形成若干个通道平面,再把平面排列起来
|                       // cvCreateImage 只能创建像素交错排列式的图像
|-- int  origin;        // 0 – 像素原点为左上角,
|                       // 1 – 像素原点为左下角 (Windows bitmaps style)
|-- int  widthStep;     // 相邻行的同列点之间的字节数    width * nChannels * depth / 8  ;
|-- int  imageSize;     // 图像的大小(字节为单位) = height*widthStep
|-- struct _IplROI *roi;// 图像的感兴趣区域(ROI). ROI非空时对图像的
|                       // 处理仅限于ROI区域.
|-- char *imageDataOrigin; // 图像数据未对齐时的数据原点指针
|                          // (需要正确地重新分配图像内存 )
|                          // (needed for correct image deallocation)
|-- int  align;         // 图像数据的行对齐: 4 or 8 byte alignment
|                       // OpenCV 中无此项,采用widthStep代替
|-- char colorModel[4]; // 颜色模型 – OpenCV中忽略此项

访问图像像素

[编辑]

(1) 假设你要访问第k通道、第i行、第j列的像素。

[编辑]

(2) 间接访问: (通用,但效率低,可访问任意格式的图像)

对于单通道字节型图像:
IplImage* img=cvCreateImage(cvSize(640,480),IPL_DEPTH_8U,1);
CvScalar s;
s=cvGet2D(img,i,j); // get the (j,i) pixel value, 注意cvGet2D与cvSet2D中坐标参数的顺序与其它opencv函数坐标参数顺序恰好相反.本函数中i代表y轴,即height;j代表x轴,即width.
printf("intensity=%f\n",s.val[0]);
s.val[0]=111;
cvSet2D(img,i,j,s); // set the (j,i) pixel value
对于多通道字节型/浮点型图像:
IplImage* img=cvCreateImage(cvSize(640,480),IPL_DEPTH_32F,3);
CvScalar s;
s=cvGet2D(img,i,j); // get the (j,i) pixel value
printf("B=%f, G=%f, R=%f\n",s.val[0],s.val[1],s.val[2]);
s.val[0]=111;
s.val[1]=111;
s.val[2]=111;
cvSet2D(img,i,j,s); // set the (j,i) pixel value
[编辑]

(3) 直接访问: (效率高,但容易出错)

对于单通道字节型图像:
IplImage* img=cvCreateImage(cvSize(640,480),IPL_DEPTH_8U,1);
((uchar *)(img->imageData + i*img->widthStep))[j]=111;
对于多通道字节型图像:
IplImage* img=cvCreateImage(cvSize(640,480),IPL_DEPTH_8U,3);
((uchar *)(img->imageData + i*img->widthStep))[j*img->nChannels + 0]=111; // B
((uchar *)(img->imageData + i*img->widthStep))[j*img->nChannels + 1]=112; // G
((uchar *)(img->imageData + i*img->widthStep))[j*img->nChannels + 2]=113; // R
对于多通道浮点型图像:
IplImage* img=cvCreateImage(cvSize(640,480),IPL_DEPTH_32F,3);
((float *)(img->imageData + i*img->widthStep))[j*img->nChannels + 0]=111; // B
((float *)(img->imageData + i*img->widthStep))[j*img->nChannels + 1]=112; // G
((float *)(img->imageData + i*img->widthStep))[j*img->nChannels + 2]=113; // R
[编辑]

(4) 基于指针的直接访问: (简单高效)

对于单通道字节型图像:
IplImage* img  = cvCreateImage(cvSize(640,480),IPL_DEPTH_8U,1);
int height     = img->height;
int width      = img->width;
int step       = img->widthStep;
uchar* data    = (uchar *)img->imageData;
data[i*step+j] = 111;
对于多通道字节型图像:
IplImage* img  = cvCreateImage(cvSize(640,480),IPL_DEPTH_8U,3);
int height     = img->height;
int width      = img->width;
int step       = img->widthStep;
int channels   = img->nChannels;
uchar* data    = (uchar *)img->imageData;
data[i*step+j*channels+k] = 111;
对于多通道浮点型图像(假设图像数据采用4字节(32位)行对齐方式):
IplImage* img  = cvCreateImage(cvSize(640,480),IPL_DEPTH_32F,3);
int height     = img->height;
int width      = img->width;
int step       = img->widthStep;
int channels   = img->nChannels;
float * data    = (float *)img->imageData;
data[i*step+j*channels+k] = 111;
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: