Это похоже на ошибку в реализации g ++ std::function
или, может быть, std::bind
, в зависимости от того, можете ли вы вызвать объект, возвращенный bind(&Foo::Bar, placeholders::_1)
с помощью foo
;если это работает:
auto fn2 = bind(&Foo::Bar, placeholders::_1);
fn2(foo);
, тогда может показаться, что реализация std::function
в g ++ не завершена.В противном случае может показаться, что реализация std::bind
является неполной.
[20.8.9.1.2] Шаблон функции bind
состояния:
template<class F, class... BoundArgs>
unspecified bind(F&& f, BoundArgs&&... bound_args);
...
Возвращает : Оболочка переадресации вызовов g
со слабым типом результата (20.8.2).Эффект g(u1, u2, ..., uM)
должен быть <em>INVOKE</em>(fd, v1, v2, ..., vN, result_of::type)
[20.8.2] Состояния требований:
Определить <em>INVOKE</em>(f, t1, t2, ..., tN)
следующим образом:
- (t1.*f)(t2, ..., tN)
когда f
является указателем на функцию-член класса T
и t1
является объектом типа T
или ссылкой на объект типа T
или ссылкой на объекттипа, производного от T
;
- ((*t1).*f)(t2, ..., tN)
, когда f
является указателем на функцию-член класса T
, а t1
не является одним из типов, описанных в предыдущемitem;
...
При связывании &Foo::Bar
возвращаемая «оболочка переадресации вызова» принимает один аргумент, u1
.Назовите его тип U1
.Далее в [20.8.9.1.2] говорится, что поскольку первый тип аргумента шаблона в BoundArgs
был типом заполнителя _1
, тип V1
равен U1&&
.
Передача std::shared_ptr<Foo>
для оболочки переадресации вызовов, возвращаемой bind(&Foo::Bar, placeholders::_1)
, следует разрешить, поскольку применяется случай 2 из [20.8.2].
EDIT: Я использую ту же версию g ++, что и вы, 4.5.2, в Windows (MinGW).Для меня следующие компиляции просто отлично:
#include <functional>
#include <memory>
#include <iostream>
using namespace std;
class Foo
{
public:
void Bar() { std::cout << "Foo::Bar" << std::endl; }
};
int main()
{
shared_ptr<Foo> foo(new Foo);
function<void(Foo*)> f1(bind(&Foo::Bar, placeholders::_1));
//function<void(shared_ptr<Foo>)> f2(bind(&Foo::Bar, placeholders::_1));
auto fn2 = bind(&Foo::Bar, placeholders::_1);
fn2(foo);
return 0;
}
Таким образом, похоже, это реализация g ++ 1070 *, которая виновата.
EDIT2: Следующие ошибки:
auto fn2 = bind(&Foo::Bar, placeholders::_1);
fn2(std::shared_ptr<Foo>(foo));
SO7408263.cpp: 19: 31: ошибка: нет совпадения для вызова '(std :: _ Bind (std :: _ Placeholder <1>)>) (std :: shared_ptr) '
Возможно, в конце концов std::bind
.