2013-02-15 5 views
4

У меня есть интерфейс, как это (за исключением очень много времени, чем это в реальном коде библиотеки)Как избежать дублирования кода со статическим полиморфизмом

struct IFoo 
{ 
    virtual void onA(A& a) = 0; 
    virtual void onB(A& a) = 0; 
    virtual void onC(A& a) = 0; 
}; 

и является общим для меня, чтобы реализовать различные слушателей IFoo. Из-за этого, я разработал вспомогательный класс, как этот:

template <class T> 
struct IFooHelper { 
    virtual void onA(A& a) { static_cast<T*>(this)->onGeneric(a); } 
    virtual void onB(B& b) { static_cast<T*>(this)->onGeneric(b); } 
    virtual void onC(C& c) { static_cast<T*>(this)->onGeneric(c); } 
}; 

так что теперь, когда у меня есть много общего поведения в качестве слушателя, вместо того, чтобы обеспечить виртуальное переопределение каждой IFoo функции I может сделать что-то вроде:

struct Fox : public IFooHelper<Fox> 
{ 
    template <class T> void onGeneric(T& t) { //do something general } 
    void onD(D& d) { //special behavior only for a type D } 
}; 

Это работает фантастически хорошо, но теперь я реализую слушатель, для которого я хочу некоторое общее поведение, а затем обновлять счетчик, скажем, какой тип вызова он был. Другими словами, исходя из допущения, я только типы A,B,C, как указано выше, мой слушатель будет:

struct Ugly : public IFooHelper<Ugly> 
{ 
    void onA(A& a) { //8 lines of common code; //update some counter for type A objs; } 
    void onB(B& b) { //8 lines of common code; //update some counter for type B objs; } 
    void onC(C& c) { //8 lines of common code; //update some counter for type C objs; } 
}; 

здесь, вызовы должны быть очень быстро (так не поиски) и в идеале я бы возможность эксплуатировать IFooHelper чтобы поднять общее поведение в методе шаблона, а затем каким-то образом все еще можно различать типы. Я думал о чем-то вроде специализированной структуры шаблона с смещениями в статическом cons char * array..or с самими значениями, которые являются char * в зависимости от T .. это лучший способ?

+0

Упование [это] (http://en.wikipedia.org/wiki/Template_method_pattern) помогает. –

+0

Как об использовании отдельного метода для общего кода, который встраивается в другие методы? – wich

+0

@wich, подумал об этом ... на данный момент я его реализовал с помощью макроса специализированных структур шаблонов со статическими смещениями в массив. –

ответ

1

Не уверен, что я полностью понимаю, что вы ищете, но я дам ему шанс. В качестве первого шага, рассмотрим следующее:

struct NotSoUgly : public IFooHelper<NotSoUgly> 
{ 
    void updateCounter(A& a) { //update some counter for type A objs; } 
    void updateCounter(B& b) { //update some counter for type B objs; } 
    void updateCounter(C& c) { //update some counter for type C objs; } 

    template <class T> void onGeneric(T& t) { 
     //8 lines of common code; 
     updateCounter(t); 
    } 
}; 

Дальнейшие улучшения возможны, если бы вы показать нам содержание updateCounter() методов мы могли бы придумать с одним родовым реализации для этого, как хорошо, но не видя кода, трудно догадаться.

+0

Спасибо, это кажется наилучшим возможным, учитывая текущую ситуацию. Я сделаю редактирование через пару часов, чтобы показать, что я закончил делать. –