|
Boost Users : |
From: Jeff F (TriumphSprint2000_at_[hidden])
Date: 2007-03-29 09:11:56
Forever Kid wrote:
> What is the correct boost::bind syntax to use with a standard
> algorithm such as find_if with an array of weak_ptrs or shared_ptrs
> to an object such as a string?
>
> My weak attempt to figure this out is below:
>
> shared_ptr<string> sp1(new string("Play "));
> shared_ptr<string> sp2(new string("with "));
> shared_ptr<string> sp3(new string("C++!"));
>
> vector<weak_ptr<string> > a_vector;
>
> a_vector.push_back(weak_ptr<string>(sp1));
> a_vector.push_back(weak_ptr<string>(sp2));
> a_vector.push_back(weak_ptr<string>(sp3));
>
> // What is the correct syntax here?
> find_if(a_vector.begin(), a_vector.end(), (bind(&equal_to<string>(),
> _1))(string("Play "));
The above has many problems unrelated to weak_ptrs.
(bind(&equal_to<string>(),_1))(string("Play "));
|----------------------------||---------------|
a b
Part "a" above is not a properly formed bind expression:
1 - you are passing the address of an equal_to<...> instance.
2 - equal_to<...> expects two arguments you supply one.
Part "b" attempts to invoke the function object resulting from Part "a", and
passes the result(if part "a" were well formed); a bool to find_if. find_if
then tries to apply operator() to the bool, which again is ill formed.
The proper bind expression for comparing a string _value_ is:
bind( equal_to<string>(), _1, string("Play ") )
To use this you'd need an indirect or transform iterator adaptor that derefs
the weak ptrs. See
http://www.boost.org/libs/iterator/doc/indirect_iterator.html
http://www.boost.org/libs/iterator/doc/transform_iterator.html
I'm not sure of the details in using an indirect iterator with weak_ptr. A
transform iterator would require you to provide a deref function, and use it
with the iterator adaptor library. This is untested code:
std::string deref_wps( weak_ptr<string> wps ){ return /* derefed wps */; }
find_if( make_transform_iterator(a_vector.begin(),&deref_wps)
, make_transform_iterator(a_vector. end(),&deref_wps)
, bind( equal_to<string>(), _1, string("Play ") )
);
Or using some of the nice operator overloading provided by bind, you can
forego the iterator adaptors:
find_if( a_vector.begin()
, a_vector. end()
, bind( &deref_wps, _1 ) == string("Play ")
);
Jeff
Boost-users list run by williamkempf at hotmail.com, kalb at libertysoft.com, bjorn.karlsson at readsoft.com, gregod at cs.rpi.edu, wekempf at cox.net