三种内存管理方式
1. 捕获装置TRAP()和TRAPD(), 用于捕获函数所产生的异常。
TRAP()的用法:
TInt err;
TRAP(err, functional());
TRAPD()的用法跟TRAP()的区别在于,不用先定义一个error,而TRAP()需要。(不知道还有没有其他区别,没有的话觉得nokia实在是有病,只用一个TRAPD()不就可以了,又方便有省事).
捕获异常后,可以用宏_ASSERT_ALWAYS(!error,User::Panic(KTxtEPOC323EX,error)),或者用函数,如
TRAPD(error,doExampleL());
if(error)
console->Printf(KFormatFailed,error);
else
console->Printf(KTxtOK);
2.清理栈
对象如果申请内存成功,进行函数操作的时候发生异常推出,则成员变量会来不及释放掉,从而造成内存泄露,因此,symbian中发明了清理栈的方式来防止这种内存泄露:
使用清理栈的时候,首先通过CleanupStack::PushL()语句将有可能发生异常的对象压入栈,相应的语句执行完成后,在把对象弹出清理栈。处理弹出对象是,清理栈规定会回收弹出的栈顶元素所指向的内存空间,从而保证执行过程中不会发生内存泄露。
3.二阶段构造,基本思想是将可能产生异常的代码包含在二阶段构造函数中,把不会产生异常的代码放在普通构造函数中
在函数中,定义static的共有静态函数NewL()和NewLC(),NewLC()中一般有一个压栈函数PushL(),可以在NewL()中Pop()出来,也可以不用,在其他函数中弹出,然后除去默认的构造函数(symbian中写成私有的),还有一个私有的二次构造函数ConstructL(),在NewLC()或者NewL()中调用。
Tips:
控制台中的main函数是E32Main(), 他调用了CallExampleL()函数,这两个函数都在CommonFrameWork.h中定义,而CallExampleL()则调用doExampleL()函数,所以你可以重写这个doExampleL()函数,并把头文件CommonFrameWork.h包含进来,这样,这个doExampleL()就可以看作当成main函数看待。
doExampleL()是个静态函数,一般用LOCAL_C标识。
一个内存管理程序的代码:
CMemoryManagement.h
#ifndef _CMEMORYMANAGEMENT_H
#define _CMEMORYMANAGEMENT_H

#include <e32cons.h>
#include <e32base.h>

class CMemoryManagement:public CBase

...{
public :
static CMemoryManagement* CMemoryManagement::NewL(TText aTText,TInt aTInt,TReal aTReal);
static CMemoryManagement* CMemoryManagement::NewLC(TText aTText,TInt aTInt,TReal aTReal);
TReal Division();
virtual ~CMemoryManagement();
TAny Print();
private:
void CMemoryManagement::ConstructL(TText aTText,TInt aTInt,TReal aTReal);
CMemoryManagement();
private:
TInt iTInt;
TReal iTReal;
TText iTText;
};


#endif
CMemoryManagement.cpp
#include "CMemoryManagement.h"

CMemoryManagement* CMemoryManagement::NewL(TText aTText,TInt aTInt,TReal aTReal)

...{
CMemoryManagement* self=NewLC(aTText,aTInt,aTReal);
CleanupStack::Pop(self);
return self;
}

CMemoryManagement* CMemoryManagement::NewLC(TText aTText,TInt aTInt,TReal aTReal)

...{
CMemoryManagement* self=new(ELeave)CMemoryManagement();
CleanupStack::PushL(self);
self->ConstructL(aTText,aTInt,aTReal);
return self;
}
void CMemoryManagement::ConstructL(TText aTText,TInt aTInt,TReal aTReal)

...{
iTInt=aTInt;
iTReal=aTReal;
iTText=aTText;
}

TReal CMemoryManagement::Division()

...{
return iTReal/2.0;
}

CMemoryManagement::CMemoryManagement()

...{

}

CMemoryManagement::~CMemoryManagement()

...{

}
TAny CMemoryManagement::Print()

...{
CConsoleBase* console;
_LIT(KTxtExampleCode,"Symbian OS Test Code");
console=Console::NewL(KTxtExampleCode,TSize(KConsFullScreen,KConsFullScreen));
_LIT(KTInt,"The TInt value is %d ");
console->Printf(KTInt,iTInt);
_LIT(KTReal,"The TReal value is %f ");
console->Printf(KTReal,iTReal);
_LIT(KTTEXT,"The TTEXT value is %c ");
console->Printf(KTTEXT,iTText);
TRAPD(error,Division())

...{
if(error)

...{
console->Printf(_L("This is a error!!"));
console->Printf(_L(" "));
}
else

...{
_LIT(KRIGHT,"No Eleave!! Value is %f");
TReal i;
i=Division();
console->Printf(KRIGHT,i);
console->Printf(_L(" "));
}
}
}
CTest.cpp
#include "CommonFramework.h"
#include "CMemoryManagement.h"

LOCAL_C void doExampleL()

...{
CMemoryManagement* iMM=CMemoryManagement::NewL('a',3,4);
CleanupStack::PushL(iMM);
iMM->Print();
CleanupStack::PopAndDestroy(iMM);

}