
David Abrahams wrote:
"Peter Dimov" <pdimov@mmltd.net> writes:
David Abrahams wrote:
I'm not sure how the bind placeholders can cause ODR violations; could you elaborate?
Simple:
// f.hpp template <class S, class T> bool f(S const& s, T const& x) { return std::find_if( s.begin(), s.end() , boost::bind(std::less<T>(), _1, x)) != s.end(); }
// t1.cpp #include "f.hpp" #include <vector> bool f1(std::vector<int> const& s, int x) { return f(s,x); }
// t2.cpp #include "f.hpp" #include <vector> bool f2(std::vector<int> const& s, int x) { return f(s,x); }
f<std::vector<int>,int> refers to a different object when it names "_1" in each translation unit.
Thanks.
Anyway, I guess we'll have to migrate to TR1 style placeholders one day, but this will break existing code.
I'm not sure it has to:
namespace bind { extern arg<1> _1; }
#1: extern implies .obj. Currently bind doesn't need a build/install phase.
namespace { // if you like using bind::_1; }
#2: using declarations of this form have a lot of potential. :-) I had in mind something like namespace boost { namespace placeholders // also sagt TR1 { inline boost::arg<1> _1() { return boost::arg<1>(); } } // placeholders } // boost #ifndef BOOST_BIND_NO_GLOBAL_PLACEHOLDERS using namespace boost::placeholders; #endif But not for 1.32, I think. First thing post-branch, maybe. ;-)