2014-09-02 614 views
2

可以使用此方法释放内存吗?Opencv - 释放内存将cv :: Mat引用计数器更改为零

while(true){ 
     Mat img = imread("C:/image.jpg"); 
     img.refcount = 0; 
     img.release(); 
    } 

如果内存以这种方式释放,会发生什么情况?假设所指出的点是安全的。

+2

也许你的意思是“*(img.refcount)= 0; “ (refcount本身就是一个指针) – MariusSiuram 2014-09-02 15:11:38

+2

你为什么要这么做? – Bull 2014-09-02 16:05:42

+4

你不会*想要手动调整refcounts;) – berak 2014-09-02 17:40:45

回答

2

如果你试图释放这样的内存,你将不会成功。查看源代码(请参阅下文),如果recount为NULL,则不执行解除分配。实际上,当用指向用户分配数据的指针构造Mat时,refcount被设置为NULL。

inline void Mat::release() 
{ 
    if(refcount && CV_XADD(refcount, -1) == 1) 
     deallocate(); 
    data = datastart = dataend = datalimit = 0; 
    size.p[0] = 0; 
    refcount = 0; 
} 

如果在另一方面,通过MariusSiuram的建议,你设定在零引用计数什么百分点,释放一定会成功。 但我不确定为什么你会这样做,因为img的析构函数会为您解除分配。

关于你提到的有关在矢量擦除垫评论,这里是一个演示:

#include<opencv2/core/core.hpp> 
#include "opencv2/highgui/highgui.hpp" 
#include <vector> 
#include <iostream> 
using namespace std; 

int main() 
{ 
    cv::Mat img = cv::imread("lena.jpg"); 
    cout << "*refcount = " << (*img.refcount) << " should be 1" << endl; 
    vector<cv::Mat> v; 
    v.push_back(img); 
    v.push_back(img); 
    v.push_back(img); 
    v.push_back(img); 
    cout << "*refcount = " << (*img.refcount) << " should be 5" << endl; 
    auto f = v.begin(); 
    ++f; 
    v.erase(f); 
    cout << "*refcount = " << (*img.refcount) << " should be 4" << endl; 
    f = v.end(); 
    --f; 
    v.erase(f); 
    cout << "*refcount = " << (*img.refcount) << " should be 3" << endl; 
    v.resize(0); 
    cout << "*refcount = " << (*img.refcount) << " should be 1" << endl; 
    img.release(); 
    cout << "refcount ptr = " << (img.refcount) << " should be 0" << endl; 
} 

输出的结果是:

*refcount = 1 should be 1 
*refcount = 5 should be 5 
*refcount = 4 should be 4 
*refcount = 3 should be 3 
*refcount = 1 should be 1 
refcount ptr = 00000000 should be 0 
+0

Tks B ...阅读您的回复后,我开始了解refcount是如何工作的。然后我只是在我的代码中进行调试,检查引用计数已更改的位置,并找到内存泄漏的位置,并在cv :: Mat对象中释放。现在我的代码工作正常。非常感谢! – rwvaldivia 2014-09-09 14:23:20