Использование bind1st для метода, который принимает аргумент по ссылке - PullRequest
14 голосов
/ 19 октября 2011

У меня есть такая структура:

struct A {
    void i(int i) {}
    void s(string const &s) {}
};

Теперь, когда я попробую это:

bind1st(mem_fun(&A::i), &a)(0);
bind1st(mem_fun(&A::s), &a)("");

Первая строка компилируется нормально, но вторая выдает ошибку:

c:\program files (x86)\microsoft visual studio 10.0\vc\include\xfunctional(299): error C2535: 'void std::binder1st<_Fn2>::operator ()(const std::basic_string<_Elem,_Traits,_Ax> &) const' : member function already defined or declared
          with
          [
              _Fn2=std::mem_fun1_t<void,A,const std::string &>,
              _Elem=char,
              _Traits=std::char_traits<char>,
              _Ax=std::allocator<char>
          ]
          c:\program files (x86)\microsoft visual studio 10.0\vc\include\xfunctional(293) : see declaration of 'std::binder1st<_Fn2>::operator ()'
          with
          [
              _Fn2=std::mem_fun1_t<void,A,const std::string &>
          ]
          c:\work\sources\exception\test\exception\main.cpp(33) : see reference to class template instantiation 'std::binder1st<_Fn2>' being compiled
          with
          [
              _Fn2=std::mem_fun1_t<void,A,const std::string &>
          ]

В чем может быть проблема? Как я мог это исправить?

Изменить:

Кажется, что любой ссылочный аргумент является проблемой. Поэтому, если я изменю метод i на void i(int &i) {}, я получу похожую ошибку.

Ответы [ 4 ]

10 голосов
/ 19 октября 2011

std :: bind1st и std :: bind2nd не принимают функторы, которые принимают ссылочные аргументы, поскольку они сами формируют ссылки на эти аргументы Вы можете

  1. используйте указатели для ввода функций вместо ссылок
  2. используйте boost :: bind
  3. принять стоимость выполнения копирования строки
6 голосов
/ 19 октября 2011

Проблема заключается в дефекте в спецификации библиотеки.

Посмотрите на этот отчет об ошибке для gcc и полученное в результате обсуждение: Ошибка 37811 - ошибка bind1st на mem_fun со ссылочным аргументом

C ++ 03 не хватало средств для создания идеальной библиотеки связывания.Эта проблема исправлена ​​в C ++ 11 с идеальной пересылкой и std :: bind.

0 голосов
/ 19 октября 2011

Изменить ссылки по указателям

#include <functional>
#include <string>

struct A {
    void i(int i) {}
    void s(const std::string *s) {}
};


int main(void)
{
    A a;
    std::bind1st(std::mem_fun(&A::i), &a)(0);
    const std::string s("");
    std::bind1st(std::mem_fun(&A::s), &a)(&s);
}
0 голосов
/ 19 октября 2011

Посмотрите на эту запись , где объясняются требования к параметрам шаблона.Как вы уже предполагали, проблема в ссылке на std :: string.Это недопустимый параметр шаблона.

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