C ++: назначение функции объекту tr1 :: function - PullRequest
2 голосов
/ 03 ноября 2011

Один из наших классов предоставляет объект обратного вызова tr1 :: function. Когда я пытаюсь назначить ему функцию-член, я получаю ошибку компилятора.

Приведенные ниже примеры не проверены и приведены только для иллюстрации:

foo.h:

class Foo()
{
public:
  Foo();
  std::tr1::function<void (int x)> F;
}

bar.h:

class Bar()
{
public:
   Bar();
   Foo* foo;
   void HookUpToFoo();
   void Respond(int x);
}

Bar.cpp:

Bar()
{
    this->foo = new Foo();
    this->HookUpToFoo();
}

void Bar::HookUpToFoo()
{
  this->foo->F = &Bar::Respond; // error
}

void Bar::Respond(int x)
{
       // do stuff
}

Ошибка компилятора, которую мы получаем, относится к строке в xrefwrap и является Ошибка 1 ошибка C2296: «. *»: Недопустимо, левый операнд имеет тип «int» C: \ Program Files \ Microsoft Visual Studio 9.0 \ VC \ include \ xrefwrap 64

.. Что я делаю неправильно при назначении делегата? Я хочу пойти по более современному маршруту и ​​использовать tr1 :: function вместо указателей на функции.

Ответы [ 2 ]

5 голосов
/ 03 ноября 2011

Функция-член принимает дополнительный скрытый параметр: this. Это делает его несовместимым с вашим function объектом, который принимает только один параметр. Вы можете привязать функцию-член к определенному экземпляру, используя bind, который также доступен в tr1:

using namespace std::tr1::placeholders;

this->foo->F = std::tr1::bind(&Bar::Respond, this, _1);

Это гарантирует, что Bar::Respond будет вызван с правильным значением, связанным с this. _1 является заполнителем для дополнительного параметра (x).

1 голос
/ 03 ноября 2011

Bar::Respond является функцией-членом, а не функцией. Его нельзя вызвать без this. Это то же самое, что и разница между void (Bar::*)(int) указателем на функцию-член и void (*)(int) указателем на функцию.

Вы можете использовать mem_fn для создания function объекта из функции-члена.

F = std::bind1st(std::tr1::mem_fn(&Bar::Respond), this);
...