1

I have a vector of shared_ptr, I want to combine boost shared_ptr and bind together.

My question is very similar to this, except that instead of "&MyClass::ReferenceFn" I would like to call "&Element::Fn".

Here is a similar piece of code:

typedef boost::shared_ptr< Vertex > vertex_ptr; 
std::set<vertex_ptr> vertices;

void B::convert()
{
...
if( std::find_if(boost::make_indirect_iterator(vertices.begin()), 
                 boost::make_indirect_iterator(vertices.end() ),  boost::bind( &Vertex::id, boost::ref(*this), _1 ) == (*it)->id() ) == vertices.end() )
}

here is the error:

no matching function for call to ‘bind(<unresolved overloaded function type>, const boost::reference_wrapper<B>, boost::arg<1>&)’

NOTE: I am limited to use the C++03.

Community
  • 1
  • 1
H'H
  • 1,638
  • 1
  • 15
  • 39
  • what error do you get ? – Piotr Skotnicki Mar 23 '16 at 15:52
  • @PiotrSkotnicki, the error is that it take (this keyword) as this pointer of class B – H'H Mar 23 '16 at 16:04
  • 2
    then perpahs you want `boost::bind(&Vertex::id, _1) == (*it)->id())`, or, `boost::bind(static_cast(&Vertex::id), _1) == (*it)->id())` (where `int` is the return type of `id`) – Piotr Skotnicki Mar 23 '16 at 16:05
  • thank you very much, if you provide you comment as an answer I will choose it as best solution. and Also will you please explain me what star means in "(Vertex::*) ? – H'H Mar 25 '16 at 16:42

1 Answers1

2

To call a member function for each object stored in a collection, you need to use a placeholder as the first bound argument of the boost::bind:

boost::bind(&Vertex::id, _1) == (*it)->id())
//                       ~^~

This way, each argument a, will be bound to a member function pointer, and called as (a.*&Vertex::id)().

However, seeing that the error message says unresolved overloaded function type, it draws a conclusion that your class Vertex can have multiple overloads of member function id. As such, the compiler is unable to tell which one it should pass as the argument of boost::bind. To solve this, use an explicit cast to a member function pointer (the asterisk after colon indicates it's a pointer to a member):

boost::bind(static_cast<int(Vertex::*)()const>(&Vertex::id), _1) == (*it)->id())
//                      ~~~~~~~~~~~~~~~~~~~~^

In the case class Vertex has multiple overloads, say:

int id() const { return 0; }
void id(int i) { }

you will use the first one for binding.

Piotr Skotnicki
  • 46,953
  • 7
  • 118
  • 160