Cocos2d-lua 内存管理

本文介绍了Cocos2d-x引擎中基于C++的内存管理机制,特别是与Lua交互时如何进行引用计数和自动回收池的使用。通过`retain()`、`release()`和`autorelease()`等方法管理对象生命周期,结合`AutoReleasePool`,实现对象的自动管理。当对象计数器减为0时,对象会被销毁。同时,文章提到了Lua对象在C++对象销毁后的处理过程。

前言


Cocos2d-x的核心框架是由C++来实现的,然后通过LuaBinding转化为Lua API。


内存管理


如下Lua代码:

local luaScene = cc.Scene:create()
local luaSprite = cc.Sprite:create("hi.png")
luaScene:addChild(luaSprite)

内部调用了C++代码:

auto cppScene = cocos2d::Scene::create();
auto cppSprite = cocos2d::Sprite::create("hi.png");
cppScene::addChild(cppSprite);

Cocos2d-x 对 sprite 的生命周期管理,并不符合一般的C++变量。而是使用一套叫做【基于引用计数的自动回收机制】。

1、引用计数(Reference Count)

Cocos2d引擎中抽象了一个基类Ref,需要引用计数管理的类都会继承自该类,Ref提供了一个计数器,当新建一个Ref实例时,计数器初始化为1。同时Ref提供了修改计数器的接口:

    Ref::retain(),计数器加一。

    Ref::release(),计数器减一。

    Ref::autorelease(),将实例添加到AutoReleasePool,在游戏的下一帧时调用release()方法。

    Ref::getReferenceCount(),返回当前计数器值。

2、自动回收池(AutoReleasePool)

所有通过create方法生成的对象,都会自动添加到默认的自动回收池中。如Node的create方法如下:

Node *Node::create()
{
    Node *ret = new Node();
    if(ret && ret->init())
    {
        ret->autorelease();
    }
    else
    {
        CC_SAFE_DELETE(ret);
    }
    return ret;
}

被加入到自动回收池中的对象,计数器在游戏的下一帧调用release()方法,使计数器减一。而如果当上面创建的sprite没有被添加入scene中,那么就会因为计数器被减为0而销毁,所以实际上,调用addChild()方法会调用sprite::retain()方法,以保证对象不会被销毁。


总结:


Cocos2d-x引擎中的对象被创建后,使用retain和release来管理对象的生命周期,结合AutoreleasePool的使用,达到了对象生命周期自动管理的目的。

一个Lua对象的销毁,其实是AutoreleasePool先把该C++对象释放,然后C++对象的析构函数再通知Lua解析器,将Lua对象内部的cobj释放。


Ps:


sprite = display.newSprite("hi.png")
-- 延迟执行
self:preformwithDelas(function()
        sprite:addTo(self)
    end, 1.0)

在上述代码中,引擎会报错:invalid ‘cobj’ in function ‘lua_cocos2dx_Node_xxxxx’

尽管在Lua中sprite变量仍然存在,但是C++层已经被销毁。


评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值