如何使用cv::dnn::Net执行深度复制?

7

我想要深度复制 cv::dnn::Net 的实例:

cv::dnn::Net n1 = cv::dnn::readNetFromONNX("");
cv::dnn::Net n2 = n1;

但是据我了解,这个类使用了隐式共享。在文档中我没有找到任何方法来实现完全复制实例的功能(例如一些copy()方法)。您知道是否有可能实现这个功能吗?


你可以再次使用 readNetFromONNX。你有深拷贝的用例吗? - Yashas
1个回答

3

为了回答您的问题,我参考了OpenCV文档(关于dnn模块)和源代码

cv::dnn::Net没有显式定义的复制或移动构造函数(和复制运算符)。该类只是接口,唯一的数据成员是指向其私有部分实现的指针。

class CV_EXPORTS_W_SIMPLE Net
{
public:
    CV_WRAP Net();  //!< Default constructor.
    CV_WRAP ~Net(); //!< Destructor frees the net only if there aren't references to the net anymore.

...

private:
    struct Impl;
    Ptr<Impl> impl;
};

所以你指出在创建 cv::dnn::Net n2 = n1; 的时候没有必要复制它,因为这只是创建了另一个指向同一实现的指针。而且如果没有任何接口来访问私有指针的实现,你几乎无法在不修改源代码的情况下访问它。
你也不能使用继承自 cv::dnn::Net 并允许设置输入参数的 cv::dnn::Model,因为它也只是一个指向实现的指针。
我想不到有哪种用例需要使用两个不同实例相同网络。看起来OpenCV开发人员也是这样做的。
在多线程环境中进行网络前向传递,可以调用cv::dnn::Net::forwardAsync(),但这只适用于intel推理引擎后端。尝试从并发线程调用cv::dnn::Net::forward()将导致运行时错误。
你可以自由地从相同的配置和模型文件创建两个网络,但我也无法想象出这样做的用例(由于内部设计优化,forwardAsync()可能会提供更好的性能)。

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接