Указатель на класс функции boost bind

class Foo 
{
    double f1( int x, std::string s1 );
    double f2( int x, SomeClass s2 );
}

Я хочу иметь возможность связывать s1 Foo.f1 без экземпляра foo для создания в сущности

typedef double (Foo::* MyFooFunc)( int ) 

MyFooFunc func1 = boost::bind( &Foo::f1, _1, _2, "some string" );
MyFooFunc func2 = boost::bind( &Foo::f2, _1, _2, SomeClass );

Затем я передаю func1 и func2 в качестве параметров другим функциям, внутри которых Foo наконец-то связывается:

void SomeOtherFunction( MyFooFunc func )
{
     Foo foo;
     boost::function< double (int) > finalFunc =
          boost::bind( func, foo, _1 );
}

Вопросы: возможно ли это? Если да, 1) как этого добиться? 2) Что такое декларация MyFooFunc?

2 ответа

Решение
typedef double (Foo::* MyFooFunc)( int );

MyFooFunc func1 = boost::bind( &Foo::f1, _1, _2, "some string" );

Результат boost::bind не указатель на член, так func1 не может быть инициализирован как таковой во второй строке. Результат boost::bind является неопределенным типом (который будет зависеть от параметров). Если вы используете C++0x, самый простой способ назвать результат вызова bind это использовать auto:

auto func1 = boost::bind( &Foo::f1, _1, _2, "some string" );

Другой простой способ (не ограниченный C++03) - просто не называть результат, а использовать его на месте:

SomeOtherFunction(boost::bind(&Foo::f1, _1, _2, "some string"));

Или вы можете использовать тип-стирание, чтобы сохранить результат boost::bind в boost::functionс которым вы, кажется, знакомы. boost::function<double(Foo&, int)> это возможность, но не единственный выбор.


Теперь нам нужно найти соответствующую подпись для SomeOtherFunction: опять же, указатель на член не может быть инициализирован из результата вызова boost::bind, так void SomeOtherFunction(MyFooFunc func); не сработает Вместо этого вы можете сделать функцию шаблоном:

template<typename Func>
void SomeOtherFunction( Func func )
{
     Foo foo;
     boost::function< double (int) > finalFunc =
          boost::bind( func, foo, _1 );
}

Если шаблон не является предпочтительным, то вы должны использовать какое-то удаление типа, например, снова boost::function,

void SomeOtherFunction(boost::function<double(Foo&, int)> const& func);

(еще раз другой boost::function типы возможны в зависимости от деталей, таких как передача ref-to-const, а не ref-to-non-const)

Попробуй это:

boost::bind(&Foo::f1, object, _1, _2);

object это экземпляр класса Foo. _1 и _2 являются заполнителями аргументов.

Другие вопросы по тегам