简单的矩阵传递即。 cv :: Mat到OpenCV2.4中的函数 [英] Simple passing of Matrices ie. cv::Mat to functions in OpenCV2.4
问题描述
我是opencv的新手,我对编码中最简单的操作之一有疑问:将值传递给函数。
I am new to opencv and I have a doubt with one of the simplest operations in coding: Passing values to functions.
继承人我想做的事,
- 在主函数中初始化一个
cv:Mat
,例如,从0到0的值50。 - 将此矩阵作为参数传递给函数
foo()
,然后简单地打印出每个元素的值。矩阵。多数民众赞成吧。
- Initialize a
cv:Mat
in the main function with say, values from 0 to 50. - Pass this matrix as an argument to a function
foo()
which in turn simply prints out the values of each element in the matrix. Thats it.
现在我已经在多个地方读过,当这些矩阵通过时,它只是传递的标题,而不是实际数据。那我怎么能够在被调用函数中读出这个矩阵的值,好像整个矩阵都被传递了一样?
Now I have read in multiple places that when these matrices are passed, it is only the header that gets passed, not the actual data. Then how am I still able to read out the values of this matrix in the called function as if the entire matrix was passed?
推荐答案
要了解发生了什么,你需要看看 C ++构造函数 ,更具体地说是 复制构造函数 。
To understand what's going on you need to take a look at C++ constructors, more specifically the copy constructor.
创建 cv时: :Mat
来自另一个 cv :: Mat
,如:
cv::Mat a = cv::imread("huge.png", 1);
cv::Mat b = a;
复制构造函数(这是一个函数)<$ c $调用c> cv :: Mat 来执行对象的副本。在我谈论复制过程中发生的事情之前,你必须意识到,由于 cv :: Mat
用于存储图像,较大的图像可能占用内存中的数百兆字节。那么 cv :: Mat
的复制构造函数在上面的示例中是复制整个标题(高度,宽度,深度信息等) a
进入 b
,而不是复制的整个数据/像素
(可能是几百MB),它只是指向(使用指针) a
的原始数据。
the copy constructor (which is a function) of cv::Mat
is called to perform the copy of the object. Before I talk about what happens in the copy procedure, you must realize that as cv::Mat
is used to store images, larger images might occupy hundreds of megabytes in memory. So what the copy constructor of cv::Mat
does in the example above is copy the entire header (height, width, depth info and others) of a
into b
, but instead of copying the entire data/pixels of a
(which might be hundreds of MB), it just points (using a pointer) to the original data of a
.
换句话说,不复制整个图像数据是优化/绩效决策。
现在,请考虑调用函数的代码,并将 cv :: Mat
作为参数传递:
Now, consider this code that calls a function and passes cv::Mat
as a parameter:
void do_something(cv::Mat src)
{
// changing src pixels will be the same as changing orig pixels
}
int main()
{
cv::Mat orig = cv::imread("huge.png", 1);
do_something(orig);
return 0;
}
如果你已经研究过如何将参数传递给函数,你知道调用 do_something(a);
将 按值传递参数 。这意味着它会尝试将 orig
的内容复制到 src
中,但是,此过程会激活复制构造函数 cv :: Mat
这不会像我刚才解释的那样制作数据的硬拷贝。
If you have studied how to pass parameters to functions, you know that calling do_something(a);
will pass the parameter by value. This means that it will try to copy the content of orig
into src
, however, this procedure activates the copy constructor of cv::Mat
which will not make a hard copy of the data as I've just explained.
解决方案这个问题?如果您正在编写 do_something()
而您只想制作 orig
的真实副本,只需创建一个新 cv :: Mat
并调用方法 copyTo()
:
Solution to this problem? If you are writing do_something()
and you just want to make a real copy of orig
, just create a new cv::Mat
and call the method copyTo()
:
void do_something(cv::Mat src)
{
cv::Mat real_copy = src.copyTo();
// operating on the data of real_copy will not affect orig
}
但请记住,如果 src
是~100MB调用 copyTo()
来使真正的副本将占用另一个~100MB的内存,这意味着在单个函数调用中,您的程序从100MB变为200MB。在设计系统时请记住这一点。祝你好运。
But remember, if src
is ~100MB calling copyTo()
to make the real copy will occupy another ~100MB of memory, which means that in a single function call your program just went from 100MB to 200MB. Keep this in mind when designing your system. Good luck.
这篇关于简单的矩阵传递即。 cv :: Mat到OpenCV2.4中的函数的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!