1. 程式人生 > >模板與成員函式指標

模板與成員函式指標

#include <iostream>

#include <list>
using namespace std;

/*包裝類,成員函式指標型別與普通函式指標型別不同,不能在類外直接定義*/
template <class T, class _Ty>
class CPtrMaker
{
public:
    //自定義成員函式指標型別
    typedef    void (T::*FuncPtr)(const list<_Ty>&);
};

/*每一段長度*/
const int PER_REPLY_LEN =  5;
/*
*1、實現容器按照指定長度分段,長度不足則按實際長度
*2、根據傳入的函式指標,顯示資料
*/
template <class T, class _Ty>
void ReplyInfor(const list<_Ty>& inforIn, void (T::*FuncPtr)(const list<_Ty>&))
{
    if(inforIn.size()== 0)
        return;
    
    list<_Ty> listCopy;
    list<_Ty>::const_iterator listIter;
    list<_Ty>::const_iterator beginIter = inforIn.begin();
    list<_Ty>::const_iterator endIter = inforIn.end();
    list<_Ty>::size_type  i = 0;

    T abj;
    CPtrMaker<T, _Ty>::FuncPtr funcPtr = FuncPtr;

    for(listIter = beginIter; listIter != endIter; ++i, ++listIter)
    {
        if(inforIn.size() <= PER_REPLY_LEN)
        {
            listCopy.resize(inforIn.size());
            copy(beginIter, endIter, listCopy.begin());

            std::cout << "容器分段,長度小於" << PER_REPLY_LEN << std::endl;
            (abj.*funcPtr)(listCopy);  //函式指標的使用方式
            break;
        }
        else if(i && !(i%PER_REPLY_LEN))
        {
            if((i+5) >= inforIn.size())
            {
                listCopy.resize(PER_REPLY_LEN);
                copy(beginIter, listIter, listCopy.begin());

                std::cout << "容器分段, 第" << i/PER_REPLY_LEN << "包" << std::endl;
                (abj.*funcPtr)(listCopy);

                listCopy.resize(inforIn.size()-i);
                copy(listIter, endIter, listCopy.begin());
                std::cout << "容器分段,最後一包" << std::endl;
                (abj.*funcPtr)(listCopy);
                break;
            }else
            {
                listCopy.resize(PER_REPLY_LEN);
                copy(beginIter, listIter, listCopy.begin());
                std::cout << "容器分段, 第" << i/PER_REPLY_LEN << "包" << std::endl;
                (abj.*funcPtr)(listCopy);
            }
            beginIter = listIter;
        }
    }
}

class CReplyInt
{
public:
    /*輸出容器中的整數*/
    void show(const list<int>& listCopy)
    {
        list<int>::const_iterator Iter;
        for(Iter = listCopy.begin(); Iter != listCopy.end(); ++Iter)
        {
            std::cout << *Iter << std::endl;
        }
    }
};

class CReplyString
{
public:
    /*輸出容器中的字串*/
    void show(const list<std::string>& listCopy)
    {
        list<std::string>::const_iterator Iter;
        for(Iter = listCopy.begin(); Iter != listCopy.end(); ++Iter)
        {
            std::cout << (*Iter).c_str() << std::endl;
        }
    }
};

//注意呼叫類中非靜態成員函式的時候,使用的是類名::函式名;而不是例項名::函式名。
class A 
{
public:
    int m_int;
    void (*m_ptr)();
    static void staticmember(){cout<<"static"<<endl;}   //static member
    void nonstatic(){cout<<"nonstatic"<<endl;}          //nonstatic member
    void nonstatic1(){cout<<"nonstatic"<<endl;}          //nonstatic member
    virtual void virtualmember(){cout<<"virtual"<<endl;};//virtual member
};

int main()
{
    list<int> listInt;
    for(int i =0; i < 4; i++)
        listInt.push_back(i);

    //定義CReplyInt類的成員函式指標
    CPtrMaker<CReplyInt, int>::FuncPtr funcInt = &CReplyInt::show;
    ReplyInfor(listInt, funcInt);

    list<std::string> listString;
    listString.push_back("zero");
    listString.push_back("one");
    listString.push_back("two");
    listString.push_back("three");
    listString.push_back("four");
    listString.push_back("five");
    listString.push_back("six");
    listString.push_back("seven");
    listString.push_back("eight");
    listString.push_back("nine");
    listString.push_back("ten");
    listString.push_back("eleven");
    listString.push_back("twelve");
    listString.push_back("thirteen");
    listString.push_back("fourteen");
    listString.push_back("fifteen");
    listString.push_back("sixteen");
    listString.push_back("seventeen");
    listString.push_back("eighteen");
    listString.push_back("nineteen");
    listString.push_back("twenty");
    listString.push_back("twenty one");
    listString.push_back("twenty two");

    //定義CReplyString類的成員函式指標
    CPtrMaker<CReplyString, std::string>::FuncPtr funcString = &CReplyString::show;
    ReplyInfor(listString, funcString);
        
    return 0;
}