如何動態儲存不同類的對象的成員函數的地址?–解決(續)

來源:互聯網
上載者:User

我現在用我自己研究的方法寫了一個類(見下面源碼),與上面提到的文章的類比較有下面一些不同:1,底層關鍵的實現我用了memcpy,他利用union結構(這也導致我的功能的薄弱)。2,我的類的一個對象可以添加多個函數,可以實現統一的調用,而他的類的一個對象綁定一個函數,但很靈活。(這都是可以改的)3,我的類的功能弱,遇到函數所屬的類有繼承,虛函數,多重繼承時就不對了,只適用單一無繼承的類函數;而他的類對類的各種關係特點都有考慮,都可以處理。總的說能就是他的好,所以我的類寫出來不是讓大家用的(當然也可以在適當時候用),而是協助大家理解C++中的委託的實現的大概方法,因為人家寫的類功能強大所以實現起來就複雜,考慮的條件就多,而我的功能簡單,實現也簡單,相對比較容易理解,所以我的是用來看的,哈哈。代碼如下:
#include <iostream>#include <vector>using namespace std;class Generic//其他類型的對象的資訊都要轉化為這個類的對象的資訊而儲存下來;{};//這個類只接受一個輸入參數的成員函數,不過改一下模板參數,//和下面相應的代碼就可以接受其他種類的函數template<class InputType,class RetType=void>class Functor{public:typedef Generic* PG;//指向對象的指標類型typedef RetType (Generic::* PGF)(InputType);//指向對象成員函數的指標類型typedef RetType (* PF)(InputType);template<class FUNCCLASS>//模板函數void Add(const FUNCCLASS* a_obj,RetType (FUNCCLASS::* a_objfunc)(InputType)){typedef RetType (FUNCCLASS::* PFF)(InputType);char tempmem[sizeof(FUNCCLASS*)]={NULL};//轉化對象資訊的中間變數GenericAndFunc* pa_GenericAndFunc=new GenericAndFunc;//儲存傳入對象資訊的對象memcpy(tempmem,&a_obj,sizeof(FUNCCLASS*));memcpy(&pa_GenericAndFunc->m_pGenericObj,tempmem,sizeof(FUNCCLASS*));//實現對象地址的儲存memset(tempmem,NULL,sizeof(FUNCCLASS));memcpy(tempmem,&a_objfunc,sizeof(PFF));memcpy(&pa_GenericAndFunc->m_pGenericFunc,tempmem,sizeof(PFF));//實現對象成員函數地址的儲存m_pGenericAndFunc.push_back(pa_GenericAndFunc);}//這裡可以添加一個Add重載函數來實現接受普通函數和靜態成員函數;void Add(PF a_func){m_pFunc.push_back(a_func);}void RunAll(InputType a_input ){vector<GenericAndFunc*>::iterator pi;for (pi=m_pGenericAndFunc.begin();pi!=m_pGenericAndFunc.end();pi++){//下面就是調用函數(這裡指標比較多比較亂)GenericAndFunc *pgaf=*pi;PG g=pgaf->m_pGenericObj;PGF pgf=pgaf->m_pGenericFunc;(g->*pgf)(a_input);//(((*pi)->m_pGenericObj)->*((*pi)->m_pGenericFunc))(a_input);}vector<PF>::iterator pfi;for (pfi=m_pFunc.begin();pfi!=m_pFunc.end();pfi++){(*pfi)(a_input);}}private:class GenericAndFunc//儲存傳入對象資訊的類{public:GenericAndFunc(){m_pGenericFunc=NULL;//儲存傳入對象的地址m_pGenericObj=NULL;//儲存傳入對象成員函數的地址}PG m_pGenericObj;PGF m_pGenericFunc;~GenericAndFunc(){//不知有沒有記憶體流失,<vector>應該會自己管理記憶體吧?}};vector<GenericAndFunc*> m_pGenericAndFunc;vector<PF> m_pFunc;};class A{public:void showA(char a_char){cout<<"A::showA "<<a_char<<endl;}void showAA(char a_char){cout<<"A::showAA "<<a_char<<endl;}};class B{public:void showB(char a_char){cout<<"B::showB "<<a_char<<endl;}static void SshowB(char a_char){cout<<"B::SshowB "<<a_char<<endl;}};class C{public:virtual void showC(char a_char){cout<<"C::virtual showC"<<a_char<<endl;}};class D : public A{public:void showD(char a_char){cout<<"D(derived from A)::showD"<<a_char<<endl;}};class E : public A,public B{public:void showE(char a_char){cout<<"E(defived from A and B)::showE"<<a_char<<endl;}};void show(char a_char){cout<<"show "<<a_char<<endl;}int main(){A a;B b;C c;D d;E e;Functor<char> a_Functor;a_Functor.Add(&a,&A::showA);a_Functor.Add(&a,&A::showAA);a_Functor.Add(&b,&B::showB);a_Functor.Add(&c,&C::showC);a_Functor.Add(&d,&D::showD);//a_Functor.Add(&d,&D::showA);a_Functor.Add(&e,&E::showE);//a_Functor.Add(&e,&E::showA);//a_Functor.Add(&e,&E::showB);a_Functor.Add(show);a_Functor.Add(B::SshowB);a_Functor.RunAll('y');}

聯繫我們

該頁面正文內容均來源於網絡整理,並不代表阿里雲官方的觀點,該頁面所提到的產品和服務也與阿里云無關,如果該頁面內容對您造成了困擾,歡迎寫郵件給我們,收到郵件我們將在5個工作日內處理。

如果您發現本社區中有涉嫌抄襲的內容,歡迎發送郵件至: info-contact@alibabacloud.com 進行舉報並提供相關證據,工作人員會在 5 個工作天內聯絡您,一經查實,本站將立刻刪除涉嫌侵權內容。

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.