操作图像

您所在的位置:网站首页 查看图片像素值大小 操作图像

操作图像

2023-11-28 20:16| 来源: 网络整理| 查看: 265

操作图像¶ 输入/输出¶ 图像¶

从文件中读入一副图像:

Mat img = imread(filename)

如果你读入一个jpg文件,缺省情况下将创建一个3通道图像。如果你需要灰度(单通道)图像,使用如下语句:

Mat img = imread(filename, 0);

将图像保存到一个文件:

Mat img = imwrite(filename); XML/YAML¶

TBD

基本图像操作¶ 获取像素的亮度值¶

要获取像素的亮度值,你必须知道图像的类型和通道的数目。如下例子展示了获取单通道灰度图(类型 8UC1)的(x, y)位置处的像素值:

Scalar intensity = img.at(x, y);

intensity.val[0] 中保存从0到255的值。现在我们看一下3通道图像如何获取像素值,颜色顺序为 BGR ( imread 返回的缺省顺序):

Vec3b intensity = img.at(x, y); uchar blue = intensity.val[0]; uchar green = intensity.val[1]; uchar red = intensity.val[2];

你可以使用同样的方法处理浮点图像(例如通对一个3通道图像进行Sobel运算得到的浮点图像):

Vec3f intensity = img.at(x, y); float blue = intensity.val[0]; float green = intensity.val[1]; float red = intensity.val[2];

同样的方法也可用于像素值的修改:

img.at(x, y) = 128;

一些OpenCV函数,例如calib3d模块中的 projectPoints 函数,需要以 Mat 的格式输入二维或者三维的点。这样的矩阵必须有且仅有一列,这样每行对应一个点,矩阵类型需要是32FC2或者32FC3。这样的矩阵可以很容易的从 std::vector 转换而来:

vector points; //... fill the array Mat pointsMat = Mat(points);

您也可以通过 Mat::at 方法来读写矩阵中的一个元素:

Point2f point = pointsMat.at(i, 0); 内存管理和参考计数(reference counting)¶

Mat 内存储了矩阵/图像的属性(行数,列数,数据类型等)以及一个指向数据的指针。因此几个 Mat 实例可以指向同一个数据。 Mat 中还记录了参考计数(reference count),这样在 Mat 被释放时就知道是否需要释放数据。这儿是一个不需复制数据就创建两个矩阵的例子:

std::vector points; // .. fill the array Mat pointsMat = Mat(points).reshape(1);

这样我们得到了一个3列的32FC1矩阵,而不是1列的32FC3矩阵。 pointsMat 使用 points 的数据,且当它释放时不会是否数据。在这个例子中,开发者需要知道 points 的生命比 pointsMat 长。如果我们需要复制数据,那么请使用 Mat::copyTo 或 Mat::clone :

Mat img = imread("image.jpg"); Mat img1 = img.clone();

在C API中,开发者必须实现创建输出图像然后再调用函数。与之相比不同的是C++ API支持空的 Mat 类型的输出参数。C++ API会调用 Mat::create 创建结果矩阵。如果矩阵是空的,那将会申请数据空间;如果非空,且大小和类型符合要求,则该函数不做任何事情;如果大小或类型不符合要求,原来的数据会被释放,然后申请新的数据空间。例如:

Mat img = imread("image.jpg"); Mat sobelx; Sobel(img, sobelx, CV_32F, 1, 0); 底层操作¶

为矩阵定义了一系列方便的操作符。我们可以将一个已经存在的灰度图像 img 变成全黑色:

img = Scalar(0);

选择感兴趣区域:

Rect r(10, 10, 100, 100); Mat smallImg = img(r);

将 Mat 转为 C API 数据类型:

Mat img = imread("image.jpg"); IplImage img1 = img; CvMat m = img;

注意此处无数据复制操作。

将彩色图像转为灰度图像:

Mat img = imread("image.jpg"); // loading a 8UC3 image Mat grey; cvtColor(img, grey, CV_BGR2GRAY);

将图像的类型从8UC1转为32FC1:

src.convertTo(dst, CV_32F); 显示图像¶

在算法开发过程中,查看算法的中间结果是非常有用的。OpenCV提供了方便查看图像的方法。类型为 8U 的图像可以使用如下方法显示:

Mat img = imread("image.jpg"); namedWindow("image", CV_WINDOW_AUTOSIZE); imshow("image", img); waitKey();

调用 waitKey() 会进入一个消息循环,来等待 image 窗口上的按键动作。 类型为 32F 的图像需要转为 8U 类型。如下:

Mat img = imread("image.jpg"); Mat grey; cvtColor(img, grey, CV_BGR2GREY); Mat sobelx; Sobel(grey, sobelx, CV_32F, 1, 0); double minVal, maxVal; minMaxLoc(sobelx, &minVal, &maxVal); //find minimum and maximum intensities Mat draw; sobelx.convertTo(draw, CV_8U, 255.0/(maxVal - minVal), -minVal); namedWindow("image", CV_WINDOW_AUTOSIZE); imshow("image", draw); waitKey(); 翻译¶

于仕琪 http://www.opencv.org.cn



【本文地址】


今日新闻


推荐新闻


CopyRight 2018-2019 办公设备维修网 版权所有 豫ICP备15022753号-3