Как передать и затем вызвать универсальные функции обратного вызова, не вызывая циклическую зависимость - PullRequest
0 голосов
/ 23 февраля 2009

Не удалось творчески укоротить заголовок:)

Я использовал вариант приведенного ниже решения, однако мне всегда было интересно, есть ли лучший / более чистый способ его реализации. Я ищу решение без повышения. Мы можем, однако, взглянуть на реализацию boost и C ++ 0x, так как это скоро будет актуально.

//Notice the use of template template parameter
template <template <typename> class Callback>   
class A {
   Callback <A> m_func;
   public:
     A (Callback <A>  func):  m_func (func) {}
     void call () { m_func(*this);}

};

template <typename T>
struct MYCallback
{
   void operator () (const T&t) {}

};


void Test()
{
   typedef A<MYCallback> AType;

   MYCallback<AType> callback;
   AType a (callback);
   a.call ();

}

Другой, более солнечный способ - использовать tr1 :: function, которая станет Дефект с новой стандартизацией:

#include <tr1/functional>


class A {
   std::tr1::function <void (const A&)>  m_func;
   public:
     template <class Callback>
     A (Callback func) :  m_func (func) {}

     void call () { m_func(*this);}

};

template <class T>
struct My_callback
{
   void operator () (const T&t) {}

};

void Test ()
{
   My_callback <A> c;
   A a (c);
   a.call ();
}

Ответы [ 3 ]

1 голос
/ 23 февраля 2009

Я всегда верю, что void * - ваш друг, когда вы хотите элегантности в этих вещах

0 голосов
/ 23 февраля 2009

Если вы просто ищете советы по очистке, я бы предложил сделать My_callback обычным классом, а не шаблоном класса. Там нет очевидной необходимости для него быть шаблоном в этом случае. Вместо этого сделайте его оператором применения шаблонным или заполните A напрямую, если My_callback имеет дело только с экземплярами A:

#include <tr1/functional>

class A {
   std::tr1::function <void (const A&)>  m_func;
   public:
     template <class Callback>
     A (Callback func) :  m_func (func) {}

     void call () { m_func(*this);}

};

struct My_callback
{
   template <class T>
   void operator () (const T&t) {}
};

int main ()
{
   My_callback c;
   A a (c);
   a.call ();
}

В остальном это выглядит довольно хорошо, как есть. Не могли бы вы более конкретно рассказать, как вы надеетесь навести порядок или упростить его?

0 голосов
/ 23 февраля 2009

Один из способов сделать это с помощью производного класса:

template <class Callback>   
class A {
   Callback m_func;
   public:
     A (Callback  func):  m_func (func){}
     void call () { m_func(*this);}

};

template <typename T>
struct MYCallback
{
   void operator () (const T&t) {}

};


struct AConcrete : public A<MYCallback<AConcrete> >
{
  template <class T>
  AConcrete(T t): A<MYCallback<AConcrete> > (t) {}
};

void Test()
{

   MYCallback<AConcrete> callback;
   AConcrete a (callback);
   a.call ();

}

PS: рекурсия жесткая с шаблонами C ++.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...