美文网首页
OpenCV 教程 08 : 访问像素的三类方法

OpenCV 教程 08 : 访问像素的三类方法

作者: wjundong | 来源:发表于2020-02-24 00:26 被阅读0次

用指针访问像素

为了简化运算,Mat 类提供了 ptr 函数可以得到图像任意行的首地址,通过调用可以看到 ptr 是一个 模板函数,它返回第 i 行的首地址

下例通过操作像素来实现缩减色彩空间

#include <opencv2/opencv.hpp>

using namespace cv;

int main(int argc, char const *argv[])
{
    Mat image = imread("2.jpg");

    int rows = image.rows;
    // 列数 x 通道数 = 每一行元素个数
    int cols = image.cols*image.channels();

    for(int i = 0; i < rows; ++i) {
        // 获取第 i 行首地址
        uchar *data = image.ptr<uchar>(i); 
        for(int j=0; j < cols; ++j)
            data[j] = data[j] / 10 * 10;
    }

    imshow("结果", image);
    waitKey(0);

    return 0;
}

运行结果

image.png

用迭代器操作像素

#include <opencv2/opencv.hpp>

using namespace cv;

int main(int argc, char const *argv[])
{
    Mat image = imread("4.jpg");

    Mat_<Vec3b>::iterator it = image.begin<Vec3b>();
    Mat_<Vec3b>::iterator itend = image.end<Vec3b>();

    for( ; it != itend; ++it) {
        (*it)[0] = (*it)[0] / 10 * 10;
        (*it)[1] = (*it)[1] / 10 * 10;
        (*it)[2] = (*it)[2] / 10 * 10;
    }
    
    imshow("结果", image);
    waitKey(0);

    return 0;
}

动态地址计算

因为每个像素都要调用一次模板函数 at() 所以该方法运行时间最多,但很方便

#include <opencv2/opencv.hpp>

using namespace cv;

int main(int argc, char const *argv[])
{
    Mat image = imread("4.jpg");

    for(int i = 0; i < image.rows; ++i)
        for(int j=0; j < image.cols; j++) {
            image.at<Vec3b>(i, j)[0] = image.at<Vec3b>(i, j)[0] / 10 * 10;
            image.at<Vec3b>(i, j)[1] = image.at<Vec3b>(i, j)[1] / 10 * 10;
            image.at<Vec3b>(i, j)[2] = image.at<Vec3b>(i, j)[2] / 10 * 10;
        }

    imshow("结果", image);
    waitKey(0);

    return 0;
}

相关文章

网友评论

      本文标题:OpenCV 教程 08 : 访问像素的三类方法

      本文链接:https://www.haomeiwen.com/subject/epkyqhtx.html