使用vector <mat>时避免内存泄漏

时间:2015-12-23 11:12:52

标签: opencv memory-management memory-leaks destructor mat

我正在尝试编写一个使用opencv Mat对象的代码,它就像这样

Mat img;
vector<Mat> images;
for (i = 1; i < 5; i++)
{
  img.create(h,w,type) // h,w and type are given correctly
  // input an image from somewhere to img correctly. 
  images.push_back(img);
  img.release()
}
for (i = 1; i < 5; i++)
  images[i].release();
然而,我似乎仍然有内存泄漏,任何人都可以告诉我为什么会这样? 我认为如果mat对象的引用计数= 0,那么应该自动释放内存

3 个答案:

答案 0 :(得分:1)

您很少需要明确调用release,因为OpenCV Mat对象会自动处理内部内存。

还要注意Mat仅复制副本会创建指向相同数据的新标头。如果原始Mat超出范围,则会留下无效矩阵。因此,当您将图像推入矢量时,请使用深层复制(clone())以避免图像进入矢量变得无效。

既然你提到过:

  

我有一个存储在Mat对象中的大型3D图像。我正在使用for循环运行它。创建一个名为“图像”的2D垫子,将切片放入图像,将图像推回到矢量图像。释放图像。然后在图像矢量上执行for循环,逐个释放所有矩阵。

您可以使用以下代码将所有切片存储到矢量中。要释放矢量中的图像,只需clear矢量。

#include <opencv2/opencv.hpp>
#include <vector>
using namespace cv;
using namespace std;

int main() 
{
    // Init the multidimensional image
    int sizes[] = { 10, 7, 5 };
    Mat data(3, sizes, CV_32F);
    randu(data, Scalar(0, 0, 0), Scalar(1,1,1));

    // Put slices into images
    vector<Mat> images;
    for (int z = 0; z < data.size[2]; ++z)
    {
        // Create the slice
        Range ranges[] = { Range::all(), Range::all(), Range(z, z + 1) };
        Mat slice(data(ranges).clone()); // with clone slice is continuous, but still 3d
        Mat slice2d(2, &data.size[0], data.type(), slice.data); // make the slice a 2d image

        // Clone the slice into the vector, or it becomes invalid when slice goes of of scope.
        images.push_back(slice2d.clone());
    }

    // You can deallocate the multidimensional matrix now, if needed
    data.release();

    // Work with slices....

    // Release the vector of slices
    images.clear();

    return 0;
}

答案 1 :(得分:1)

请尝试使用此代码,这基本上就是您所做的:

postgres

第一次调用testFunction后,内存将被泄露&#34;这样应用程序在我的设备上消耗的内存增加了4 KB。但不是更多&#34;泄漏&#34;在额外打电话给我之后......

所以这看起来你的代码还可以,而且#34;内存泄漏&#34;与该矩阵的创建和发布无关,但可能与某些&#34;全球&#34; openCV库或C ++中发生的事情,以优化未来的函数调用或内存分配。

答案 2 :(得分:1)

我在迭代openCV mat时遇到了同样的问题。内存消耗可以是1.1G,然后通过警告没有内存来停止。在我的程序中,有一些宏#define new new( FILE LINE ),与某些std lib崩溃。所以我删除了所有关于new / delete的重载运算符。调试时,没有错误。但是当它运行时,我得到了#34; Debug Assertion Failed! Expression: _pFirstBlock == pHead&#34;。遵循指示 Debug Assertion Error in OpenCV 我将设置从MT(发布)/ MTd(调试)更改为

Project Properties >> Configuration Properties >> C/C++ >>代码生成并将运行时库更改为:

多线程调试DLL(/ MDd),如果您正在构建代码的调试版本。 多线程DLL(/ MD),如果您正在构建代码的发行版本。

内存泄漏消失了。内存消耗 38M