Le 20/04/13 17:03, Olaf Peter a écrit :
Hello,
g++ (GCC) 4.6.3 20120306 (Red Hat 4.6.3-2)
and maybe the last changes ... breaks my code now which is basically:
namespace {
struct id_string { static boost::once_flag flag; typedef std::map
map_type; ... static void do_init(token_id_string& self) { insert(self.m_map)(x, "y")(...) ; }
std::string const& operator()(id::type id) const { boost::call_once(flag, &id_string::do_init, *this);
map_iterator s = m_map.find(id); ... } };
Hi,
the error
/usr/local/include/boost/thread/detail/invoke.hpp:406:65: error: invalid
initialization of non-const reference of type '{anonymous}::id_string&'
from an rvalue of type '{anonymous}::id_string'
says you that the parameter (const) can not be used where a non-const is
expected.
Shouldn't the operator be declared non-const
std::string const& operator()(id::type id) ;
In addition if you want to pass a reference you would need to use
boost::ref().
The following compile well without the patch
struct id_string
{
static boost::once_flag flag;
static void do_init(id_string & )
{}
void operator()()
{
boost::call_once(flag, &id_string::do_init, boost::ref(*this));
}
};
Note that the following compiles
struct id_string
{
static boost::once_flag flag;
static void do_init(id_string & )
{}
void operator()()
{
std::bind(&id_string::do_init, std::ref(*this))();
}
void operator()(int) const
{
std::bind(&id_string::do_init, *this)();
}
};
I would expect that the preceding fails as *this is a 'id_string const&'
and do_init expects an 'id_string &'.
This would explain why with the patch it worked as the patch was calling
to std::bind.
But if make use of the class
{
id_string id;
//id();
id(1);
}
I get the following error
gcc.compile.c++
/tmp/bin.v2/boost/bin.v2/libs/thread/test/call_once_p.test/gcc-4.6.1.0x/debug/threading-multi/sync/mutual_exclusion/once/call_once/call_once_pass.o
In file included from /usr/include/c++/4.6/functional:56:0,
from ../../../boost/thread/detail/invoke.hpp:34,
from ../../../boost/thread/pthread/once_atomic.hpp:17,
from ../../../boost/thread/once.hpp:20,
from sync/mutual_exclusion/once/call_once/call_once_pass.cpp:26:
/usr/include/c++/4.6/tuple: In constructor ‘constexpr
std::_Head_base<_Idx, _Head, false>::_Head_base(const _Head&) [with
unsigned int _Idx = 0u, _Head = id_string]’:
/usr/include/c++/4.6/tuple:162:44: instantiated from ‘constexpr
std::_Tuple_impl<_Idx, _Head, _Tail ...>::_Tuple_impl(const _Head&,
const _Tail& ...) [with unsigned int _Idx = 0u, _Head = id_string, _Tail
= {}]’
/usr/include/c++/4.6/tuple:423:24: instantiated from ‘constexpr
std::tuple<_T1>::tuple(const _T1&) [with _T1 = id_string]’
/usr/include/c++/4.6/functional:1186:70: instantiated from
‘std::_Bind<_Functor(_Bound_args ...)>::_Bind(_Functor&&, _Args&& ...)
[with _Args = {const id_string&}, _Functor = void (*)(id_string&),
_Bound_args = {id_string}]’
/usr/include/c++/4.6/functional:1450:41: instantiated from ‘typename
std::_Bind_helper<_Functor, _ArgTypes>::type std::bind(_Functor&&,
_ArgTypes&& ...) [with _Functor = void (*)(id_string&), _ArgTypes =
{const id_string&}, typename std::_Bind_helper<_Functor,
_ArgTypes>::type = std::_Bind