OpenCV 3:如何将 cv::Mat 作为可选参数传递

Posted

技术标签:

【中文标题】OpenCV 3:如何将 cv::Mat 作为可选参数传递【英文标题】:OpenCV 3: How to pass cv::Mat as an optional argument 【发布时间】:2017-06-28 12:45:20 【问题描述】:

我想用 C++ 编写一个将矩阵作为可选参数的函数。如果用户在调用函数时最终传递了矩阵,它将被函数修改,所以我正在实现引用传递。

根据这个previous question接受的答案,这可以通过将默认值设为空Mat来完成,例如:

void foo(..., cv::Mat &matrix = cv::Mat()) 
    // code

    return;

但是,当我尝试在 OpenCV 3.2 中编译它时,我从 'cv::Mat' 类型的右值中得到“无效初始化类型为 'cv::Mat&' 的非常量引用”错误。

自 OpenCV 2.4 以来此功能是否发生了变化,或者问题可能出在其他地方?

【问题讨论】:

不幸的是,您设法使用了该问题的错误部分,与第一句话中所说的相矛盾。 确实,该链接上接受的答案部分错误。也许我们应该解决那个问题,然后将这个标记为重复? 我没有在我的原始帖子中指定,但我的问题源于尝试导入其他人的代码(来自 github),该实现在多个函数中使用。这与我引用的线程相结合,使我相信可能有一个元素使它起作用,但我不知何故失踪了。可能是我太相信人了,但为什么他们会上传4000多行的源代码,甚至懒得先检查它是否有效? 【参考方案1】:

我可能是错的,因为我是这些问题的初学者,但这是我的想法。 您想通过 ref 传递一个可选参数。问题是带有符号 & 的引用是对左值的引用,它是一个存在的对象。 C++ 不允许您编写的内容,因为matrix 是一个右值,它是一个临时对象,没有与之关联的实际内存地址。 您可以通过cv::Mat &matrix = cv::Mat() 的唯一方法是对其进行 const-ing,const cv::Mat &matrix = cv::Mat() 这当然不是您需要的。

恕我直言,最简单的解决方案是重载您的函数定义,以便您拥有

void foo(...args); void foo(...args, cv::Mat &matrix);

希望对你有帮助

【讨论】:

是的,就是这样做的。考虑提供实现。应该是这样的: cv::Mat dummy; foo(..., dummy); 。还使用 4 空格缩进格式化您的代码。【参考方案2】:

这是因为 C++ 不允许您使用右值初始化非常量引用。

所以你可以:

1) 将引用设为 const -- 不适合您,因为您想更改函数中矩阵的内容

2) 在您的模块中全局存储一个cv::Mat init 变量:

static const cv::Mat g_mat = cv::Mat();

void foo(..., cv::Mat &matrix = g_mat) 

【讨论】:

以上是关于OpenCV 3:如何将 cv::Mat 作为可选参数传递的主要内容,如果未能解决你的问题,请参考以下文章

opencv使用cv::Mat时,如何修改某个像素点的RGB分量

OpenCV 中的矩阵乘法 - 结合 cv::Mat 和 cv::Scalar 对象

为 svm::predict 准备 cv::mat

OpenCV Mat 数据成员访问

OpenCV:将不同的向量附加为一行

在 Librealsense SDK 中将 OpenCV Mat 转换为 Realsense 的帧类型