昨日やった自前仮想関数のよーな仕組みはCRTPを使うとシンプルにできる場合が多い。

まあ、とにかくソース。

#include "stdafx.h"
#include <Jam/Type.hpp>
#include <iostream>
#include <map>

using namespace std;
using namespace jam;

template <typename Base>
void FInvoker(Base pd)
{
    ToExact(pd).f();
}

template <typename TBottom=Bottom>
struct SuperBase:public Void<SuperBase>
{
    virtual ~SuperBase(){};
};

template <typename TBottom=Bottom>
struct A:public SuperBase<A>
{
    void f()
    {
        cout << "A" << endl;
    };
};

template <typename T>
void CallFUsingBase(SuperBase<T>& base)
{
    FInvoker(base);
}

int _tmain(int argc, _TCHAR* argv[])
{
    A<> a;

    CallFUsingBase(a);
	return 0;
}

ちなみにJam/Type.hppというのは自分ライブラリのヘッダで、ToExactとかVoidの定義がされています。

このへん詳しくはPaserry's Programing Cafe 4-3CRTPと名前の修飾を見てください。

昨日の汚いソースに比べるとかなりシンプルになる。しかしその一方で、こちらで作った機能の実装が簡単になるという理由で

使用する側(この場合たとえばSuperBaseとかAクラスを作った人)にCRTPを強制するというのはどうかと思う。