cocos2d-x内存管理初步窥探之retai…

来源:互联网 发布:nfc软件下载官方网站 编辑:程序博客网 时间:2024/05/18 18:01
   今天在使用CCArray的时候发现,在一个类中使用CCArray作为一个成员时,CCArray总会在初始化之后总会很诡异地被释放掉了,于是找了一些相关的博文看了一下,也算是对cocos2d-x中的一些内存管理规则有了更深刻的理解。
   aretain、release和autorelease都是继承自CCObject这个基类的,具体负责的就是一些关于内存管理的工作。每个CCObject在被初始化时内部都有一个计数器用来记载这个object被多少个人使用着。这计数器在一个object被new出来的时候初始化为1,调用一次retain可以使计数器+1,调用一次release则相反。调用一次release之后如果计数器变为0,则这个object会被析构释放掉。autorelease是一种特殊的release,特殊在于它不会马上release,而会在游戏主循环的时候release。调用的了autorelease的对象会被放入一个管理池,以后就不用我们再手动去release它,系统会帮我们完成这个工作。
   回到我们的问题,为什么CCArray会被释放掉呢?原因是一般来说CCArray只会作为一个类的成员,不会被其他的CCObject所获取,不像CCSprite和CCLayer可以被当做儿子卖个某一个父亲。而CCArray的create函数里面调用了autorelease(大部分类都是这样的,例如CCSprite和CCLayer),所以如果没有别的对象去获得这个对象,那么CCArray就会在第一帧的时候被析构掉。所以我们应该在类的初始化函数中这样写:
this->objects = CCArray::createWithCapacity(30);
this->objects->retain();
表示当前这个对象获得了CCArray,使CCArray的计数器+1。那么下一帧的时候才不会被析构掉。当然我们在这个类的析构函数中应该加上
this->objects->release();
才能够彻底析构掉CCArray;
   我的理解是,你生成了一个对象,那么它的引用计数器就是1.其他对象获得了它,计数器就要+1,被人抛弃时计数器要-1.调用autorelease理论上已经-1了,但是不是马上减,而是在游戏主循环的时候减。所以我们要在进入主循环之前让它被别的对象获得,才不会被析构掉。就像CCSprite,一般来说我们都会在构造之后把它add到父类节点,于是它就被别人获得了,从而不会被析构。而CCArray一般来说不会被add到其他节点,所以我们要手动retain一次,才能让它不被析构。

0 0
原创粉丝点击