IplImage 封装释放

IplImage是openCV库中很重要的一个结构体,库中的图像都是保存为这个结构体后再进行操作的,具体结构如下:

</pre><pre>

typedef struct _IplImage
{
int nSize;                /* IplImage大小 */
int ID;                  /* 版本 (=0)*/
int nChannels;           /* 大多数OPENCV函数支持1,2,3 或 4 个通道 */
int alphaChannel;        /* 被OpenCV忽略 */
int depth;               /* 像素的位深度: IPL_DEPTH_8U, IPL_DEPTH_8S, IPL_DEPTH_16U,IPL_DEPTH_16S, IPL_DEPTH_32S, IPL_DEPTH_32F and IPL_DEPTH_64F 可支持 */
char colorModel[4];      /* 被OpenCV忽略 */
char channelSeq[4];      /* 同上 */
int dataOrder;           /* 0 - 交叉存取颜色通道, 1 - 分开的颜色通道. cvCreateImage只能创建交叉存取图像 */
int origin;              /* 0 - 顶—左结构,1 - 底—左结构 (Windows bitmaps 风格) */
int align;               /* 图像行排列 (4 or 8). OpenCV 忽略它,使用 widthStep 代替 */
int width;               /* 图像宽像素数 */
int height;              /* 图像高像素数*/
struct _IplROI *roi;     /* 图像感兴趣区域. 当该值非空只对该区域进行处理 */
struct _IplImage *maskROI; /* 在 OpenCV中必须置NULL */
void *imageId;             /* 同上*/
struct _IplTileInfo *tileInfo; /*同上*/
int imageSize;           /* 图像数据大小(在交叉存取格式下imageSize=image->height*image->widthStep),单位字节*/
char *imageData;         /* 指向排列的图像数据 */
int widthStep;           /* 排列的图像行大小,以字节为单位 */
int BorderMode[4];       /* 边际结束模式, 被OpenCV忽略 */
int BorderConst[4];      /* 同上 */
char *imageDataOrigin;   /* 指针指向一个不同的图像数据结构(不是必须排列的),是为了纠正图像内存分配准备的 */
}IplImage;

由cvCreateImage()来创建包含头与数据内存,而cvCreateImageHeader则是只创建结构头,当可以预先分配好内存然后使用cvSetData影射到IplImage上。正是这个结构非常重要,但是很人在使用IplImage对象时申请了内存会经常忘记释放内存。我在下提供一个封装好的IplImage类:

class  CVImage
{
public :
	CVImage();
	CVImage(unsigned int width, unsigned int height, unsigned short depth, unsigned short nChannels = 3);
	CVImage(CVImage& img);
	~CVImage();

	void ReleaseImage();
	int Resize(unsigned int width, unsigned int height, unsigned short depth, unsigned short nChannels = 3);

	operator IplImage*() { return m_image; };
	inline IplImage* GetImage() { return m_image; };

private:
	IplImage* m_image;
};
CVImage.cpp
CVImage::CVImage() : m_image(NULL)
{
}

CVImage::CVImage( unsigned int width, unsigned int height, unsigned short depth, unsigned short nChannels ) : m_image(NULL)
{
	Resize(width, height, nChannels);
}

CVImage::CVImage( CVImage& img)
{
	IplImage* tmpImg = img.GetImage();

	if(m_image)
	{
		if(m_image->width != tmpImg->width || m_image->height != tmpImg->height)
		{
			cvReleaseImage(&m_image);
		}
	}
	m_image = cvCloneImage(tmpImg);
}

CVImage::~CVImage()
{
	ReleaseImage();
}

void CVImage::ReleaseImage()
{
	if(m_image)
	{
		cvReleaseImage(&m_image);
	}
}

int CVImage::Resize( unsigned int width, unsigned int height, unsigned short depth, unsigned short nChannels)
{
	if(0 == width || 0 == height || 0 == depth || 0 == nChannels)
		return -1;

	if(m_image)
	{
		if(width != m_image->width || height != m_image->height)
			ReleaseImage();
	}
	m_image = cvCreateImage(cvSize(width, height), depth, nChannels);

	return NULL == m_image ? -1 : 0;
}
时间: 2024-10-20 20:15:48

IplImage 封装释放的相关文章

[转帖] CvMat,Mat和IplImage之间的转化和拷贝

原文地址: http://blog.csdn.net/holybin/article/details/17711013 在OpenCV中Mat.CvMat和IplImage类型都可以代表和显示图像. IplImage由CvMat派生,而CvMat由CvArr派生即CvArr -> CvMat -> IplImage,Mat类型则是C++版本的矩阵类型(CvArr用作函数的参数,无论传入的是CvMat或IplImage,内部都是按CvMat处 理). 其中Mat类型侧重于计算,数学性较高,Ope

OpenCV(C++接口)学习笔记1-图像的读取、显示、保存

OpenCV在2.0版本之后添加了C++接口函数,之前学习的都是C语言的接口函数,现在OpenCV已经发展到2.4.9版本了,所以决定学习C++接口函数,跟上节奏. 1.创建图像 cv::Mat image; 采用类cv::Mat来定义图像变量或矩阵变量. 当然你也可以指定图像的大小: cv::Mat img(240,320,CV_8U,cv::Scalar(100)); 参数CV_8U中的U代表unsigned,而S代表signed.对于三通道彩色图像可以用CV_8UC3.你也可以声明16或3

OpenCV中数据转换

在OpenCV中Mat.CvMat和IplImage类型都可以代表和显示图像.IplImage由CvMat派生,而CvMat由CvArr派生即CvArr -> CvMat -> IplImage,Mat类型则是C++版本的矩阵类型(CvArr用作函数的参数,无论传入的是CvMat或IplImage,内部都是按CvMat处理).其中Mat类型侧重于计算,数学性较高,OpenCV对Mat类型的计算也进行了优化:而CvMat和IplImage类型更侧重于"图像",OpenCV对其

手动封装OpenCV1.0的IplImage读取保存功能遇到的小问题

最近准备重新学习图像处理的知识,主要目的是自己实现一遍图像处理的算法,所以除了读取.保存图像外的操作都自己写,没想到直接封装OpenCV的读取.保存功能的第一步就出错.关键代码如下 void MyImage::Clear() { if (m_pImg != nullptr) { std::cout << "释放内存" << std::endl; delete m_pImg; m_pImg = nullptr; } } 其中m_pImg是IplImage*类型,析

Objective-C----MRC内存管理 、 自动释放池 、 面向对象三大特性及封装 、 继承 、 组合与聚合

1 MRC练习 1.1 问题 引用计数是Objective-C语言采用的一种内存管理技术,当一个对象被创建在堆上后,该对象的引用计数就自动设置为1,如果在其它对象中的对象成员需要持有这个对象时,则该对象的引用计数被加上1,此时如果该对象被释放,内存管理程序将首先把该对象的引用计数减1,然后判断该对象的引用计数是否为0,由于其它对象在持有该对象时将引用计数加了1,所以此时该对象的引用计数减1后不为0,则内存管理程序将不会释放该对象.直到持有该对象的其它对象也被释放时,该对象的引用计数再次减1,变为

opencv之深拷贝及浅拷贝,IplImage装换为Mat

一.(1)  浅拷贝: Mat B; B = image  // 第一种方式 Mat C(image); // 第二种方式 这两种方式称为浅copy,是由于它们有不同的矩阵头,但是它们共享内存空间,即指向一个矩阵.当图像矩阵发生变化时,两者相关联,都会变化. (2)深拷贝 Mat B,C; B = image.clone();       // 第一种方式 image.copyTo(C); // 第二种方式 深拷贝是真正的copy了一个新的图像矩阵,此时image,B,C三者相互没有影响. 二.

python基础--接口与归一化设计、封装、异常、网络编程

1 接口与归一化设计 1.1 归一化概念: 归一化的好处: 1.归一化让使用者无需关心对象的类是什么,只需要知道这些对象都具备某些功能就可以了,这极大降低了使用者的使用难度. 2.归一化使得高层的外部使用者可以不加区分的处理所有接口兼容的对象集合 继承的两种用途 一:继承基类的方法,并且做出自己改变或者扩展(代码重用):实践中,继承的这种用途意义并不很大,甚至常常是有害的.因为它使得子类与基类出现强耦合. 二:声明某个子类兼容于某基类,定义一个接口类(模仿java的Interface),接口类中

C# .NET更智能的数据库操作的封装

前述: 对数据库操作的封装,相信网络上已经有一大堆,ORM框架,或者是.NET本身的EF,都很好的支持数据库操作.这篇文章是分享自己所思考的,对数据库操作的简单封装.我对于这篇文章,认为被浏览者所关注重点的是怎么分析设计数据库操作封装,代码是其次.而且,这是我第一篇文章,为了想好怎么实现花了些天,代码是博客发表时现写的.所以我想,使用可能还有bug,而且没有try catch异常的设计. 这个框架我理应做到对数据库无关,无论是哪个数据库都能够使用.不过,重点在于分析,而不是代码.所以,为了更好的

[分享] RT7LITE精简后无法封装解决办法

eagleonly 发表于 2016-6-9 11:00:01  https://www.itsk.com/forum.php?mod=viewthread&tid=368090&highlight=%BE%AB%BC%F2 经过三天多十几次失败,终于找到了RT7LITE的毛病!它一打开系统就生成了这些影响封装的东东,现在找到它,并消灭了! 用RT7LITE精简后封装失败 方法一.精简完成前处理1.首先,在RT7LITE中设置好临时文件夹(它默认的文件夹不好找),如C:\Temps,让它处