cv :: Mat的发布方法

时间:2013-04-08 07:30:25

标签: c++ opencv free mat

我想确认cv::Mat::release()方法在C编程中是否与free()类似,即它从内存中释放Matrix数据。

特别是,我想了解此方法在内存泄漏方面的行为,并确保may程序中没有泄漏。

4 个答案:

答案 0 :(得分:6)

如果引用计数器等于1,则是,cv::Mat::release()将其减少为零并释放结构(如C中的free)。

如果引用计数器大于1(即,有一些其他对象对结构感兴趣),那么cv::Mat::release()递减引用计数器。

您可以通过调用cv::Mat方法来递增cv::Mat::addref()结构的引用计数器(即,标记您对它感兴趣并且不希望它被释放)。

答案 1 :(得分:4)

您不必手动释放cv :: Mat对象,因为它是自动管理的,除非您已从Iplimage初始化Mat,在这种情况下您应该手动释放它deallocate()。

请参阅此主题。

openCV mixing IplImage with cv::Mat

答案 2 :(得分:3)

我使用像这样的代码结构(使用C ++的OpenCV)进行内存泄漏:

int i;
while(true){
    Mat x = imread("C:/pics"+i+".jpg");
    //do something with x
}

经过100次左右的迭代,它总是崩溃,然后我把代码更改为:

int i;
while(true){
    Mat x = imread("C:/pics"+i+".jpg");
    //do something with x
    x.refcount = 0;
    x.release();
}

它停止了崩溃并进行了完整的迭代。但是,当手动将refcount设置为0时,您必须确定不再需要该对象。这可能是某人拒绝投票的原因,但我用这种方法解决了我的问题。那么为什么我不能分享呢?

答案 3 :(得分:0)

以下程序片段测试Mat :: release()的行为 (改编自opencv-org-answer

using namespace std;
using namespace cv;

int main(int argc, char **argv) {
    cout << "test_mat_release.cpp" << endl;

    {
        //memory is released
        const char *pzInputImg = "data/em_sample.png";

        Mat img;
        img = imread(pzInputImg);
        assert(img.data);
        img.release();
        assert(!img.data);
    }
    {
        //memory is released
        Mat img(100, 100, CV_32FC1);
        assert(img.data);
        img.release();
        assert(!img.data);
    }

    {   
        //Since Mat does not owns data , data is not released
        //you have to explicitly release data
        int cols=17;
        int rows=15;
        unsigned char * data = new unsigned char[rows*cols*3];
        Mat img(rows, cols, CV_8UC3, data);
        assert(img.data);
        img.release();
        assert(!img.data);
        delete [] data;
    }



    Mat imgRef;
    {
        //memory is not released
        //since there img.data is now shared with imgRef
        Mat img(100, 100, CV_32FC1);
        imgRef=img;
        assert(img.data);
        assert(img.data == imgRef.data);
        img.release();
        assert(img.empty());
        assert(!img.data);
        //img.data is NULL, but imgRef.data is not NULL, so data is not de-allocated
        assert(!imgRef.empty());
        assert(imgRef.data);
    }
    return 0;
}