好吧,C++里没有匿名函数,看由Pas生成的HPP文件,你会发现它要你实现一个Interface,好在C++的类型声明是随时随地可以进行的,所以对应的实现步骤如下:
1、声明一个类,继承自TCppInterfacedObject<匿名函数类型>以实现匿名函数对应的接口,你愿意写成interface也无所谓,在C++中,struct和class实际上并没啥本质的区别,而interface只是struct的一个别名而已。
class TMyHandler:public TCppInterfacedObject<TMyAnEvent>
{
public:
void __fastcall Invoke(...你的匿名函数参数)
{
你的匿名函数实现代码
}
}在这里不要指望象Delphi的匿名函数一样直接访问局部变量,C++的类受C++限制。
2、在需要匿名函数的地方,new 一个你的类的实例,这个实例不需要你去释放,它是一个智能指针,然后就OK了。
示例如下:
void __fastcall TForm1::Button1Click(TObject *Sender){
class TMyEvent:public TCppInterfacedObject<TQXMLObjectPropFilterEvent>
{
public:
void __fastcall Invoke(TQXMLNode* ASender, System::TObject* AObject, System::UnicodeString APropName, bool &Accept)
{
if (APropName=="Enabled")
Accept=False;
else
Accept=True;
}
};
TQXMLNode *AXML=new TQXMLNode;
AXML->Add("Button1",Button1,False,new TMyEvent);
ShowMessage(AXML->Encode(True,L" ");
delete AXML;
}是不是感觉上面的代码看着有点乱,好吧,万能的宏出马了:
#define DELPHI_ANON(AType,ATypeName,Code) \
class ATypeName:public TCppInterfacedObject<AType>\
{\
public:\
void __fastcall Invoke##Code\
};上面的代码也就变成了:
void __fastcall TForm1::Button1Click(TObject *Sender)
{
DELPHI_ANON(TQXMLObjectPropFilterEvent,TMyEvent,
(TQXMLNode* ASender, System::TObject* AObject, System::UnicodeString APropName, bool &Accept)
{
if (APropName=="Enabled")
Accept=False;
else
Accept=True;
}
);
TQXMLNode *AXML=new TQXMLNode;
AXML->Add("Button1",Button1,False,new TMyEvent);
ShowMessage(AXML->Encode(True,L" ");
delete AXML;
}实际上,一般情况下TMyEvent这个类型也不是我们关心的,我们更关心的是一个变量名,也就引申出下一个版本:
#define DELPHI_ANON(AType,Code,AVar) \
class AType##AVar:public TCppInterfacedObject<AType>\
{\
public:\
void __fastcall Invoke##Code\
} *AVar=new AType##AVar
那么上面的代码就会变为:
void __fastcall TForm1::Button1Click(TObject *Sender)
{
DELPHI_ANON(TQXMLObjectPropFilterEvent,TMyEvent,
(TQXMLNode* ASender, System::TObject* AObject, System::UnicodeString APropName, bool &Accept)
{
if (APropName=="Enabled")
Accept=False;
else
Accept=True;
},ACallback
);
TQXMLNode *AXML=new TQXMLNode;
AXML->Add("Button1",Button1,False,ACallback);
ShowMessage(AXML->Encode(True,L" ");
delete AXML;
}QString新版已经内置了后一种形式的声明,当然如果有更好的办法,我会毫不犹豫的替换掉,不过目前我暂时没有。如果你有更好的实现办法,欢迎提供建议。我觉得通过STL也许有一定的希望,但我没想出来。也许你知道,不要吝啬你的智慧,告诉我吧。
