protobuf内存泄漏解决办法

1.protobuf对象是如何释放(数组)内存的?(本文只针对C++)

        毫无疑问是,通过调用析构函数。只要让protobuf定义的对象调用析构函数,无论嵌套了多少层数据、包含了多少个数组都可以释放new出来的内存。

2.protobuf对象Clear()接口和STL容器中的clear()接口的有何区别?

        我们习惯使用STL模板中各类容器(vector,map,set),而不用考虑底层对内存的使用。无论装在容器中的数据如何复杂如何庞大,只要能执行clear()就可以一了百了。

        但是,相同情况用到protobuf缺不尽然。protobuf对象的Clear()操作,只是反复调用memset执行内存重置为0的操作,这就好比将电脑C盘格式化,但C盘的容量并没有改变。

3.protobuf对象作为成员变量,如何释放内存?

        借助智能指针shared_ptr的reset()接口调用析构函数。

举例说明:

protobuf协议定义如下,ConfigItem里面包含一个SubItem数组,在测试例子中调用ConfigItem中add_items() 填充1000条数据。
 

package proto;

message SubItem
{
	required int32 id = 1;
	required int32 type = 2;
	required int32 value = 3;
}

message ConfigItem
{
	repeated SubItem items = 1;
}

测试C++代码:

#include
#include"client.pb.h"

using std::shared_ptr;

void readCfg_verson1()
{
	proto::ConfigItem config;
	for ( int idx = 0; idx < 1000; idx++ )
	{
		auto item = config.add_items();
		item->set_id(idx);
		item->set_type(idx);
		item->set_value(idx);
	}
}

void readCfg_version2()
{
	proto::ConfigItem *pconfig = new proto::ConfigItem;
	for ( int idx = 0; idx < 1000; idx++ )
	{
		auto item = pconfig->add_items();
		item->set_id(idx);
		item->set_type(idx);
		item->set_value(idx);
	}
	delete pconfig;
}

class Foo
{
public:

	Foo():pconfig_(new proto::ConfigItem){}

	shared_ptr pconfig_;

	void readCfg_version3()
	{
		for ( int idx = 0; idx < 1000; idx++ )
		{
			auto item = pconfig_->add_items();
			item->set_id(idx);
			item->set_type(idx);
			item->set_value(idx);
		}
	}
};

int main(void)
{
	//1.protobuf对象作为栈对象自动析构
	readCfg_verson1();

	//2.protobuf对象堆对象使用delete手动析构
	readCfg_version2();

	//3.protobuf对象作为成员变量借用shared_ptr的reset()接口调用析构函数
	Foo* proom = new Foo();
	proom->readCfg_version3();

	//千万注意:使用protobuf自带的Clear()函数,相当于对C数组进行memset操作,跟STL容器的clear()接口作用不一样
	proom->pconfig_->Clear();

	//正确做法://借助智能指针shared_ptr的reset()接口调用析构函数
	proom->pconfig_.reset(new proto::ConfigItem);

	//todo ...

	return 0;
}

你可能感兴趣的:(C++,protobuf,内存泄漏,c++)