Повысить навязчивый unordered_set, прерванный в 1.48 с GCC в режиме C++11
Unordered_set в Boost Intrusive не работает, если вы выполняете ванильную установку Fedora 17, которая поставляется с GCC 4.7 и Boost 1.48, и используете режим C++11. На Fedora 16, которая поставляется с GCC 4.6.2 и Boost 1.47, это работает. Это нарушает реальный код и даже нарушает пример в официальной документации:
#include <boost/intrusive/unordered_set.hpp>
using namespace boost::intrusive;
struct MyClass : public unordered_set_base_hook<>
{};
typedef unordered_set<MyClass>::bucket_type bucket_type;
typedef unordered_set<MyClass>::bucket_traits bucket_traits2;
int main()
{
bucket_type buckets[100];
unordered_set<MyClass> uset(bucket_traits2(buckets, 100)); // FAILS
}
Сообщение об ошибке:
/usr/include/boost/intrusive/hashtable.hpp:227:65: ошибка: использование удаленной функции 'constexpr boost::intrusive::detail::bucket_traits_impl >::type>::bucket_traits_impl(const boost::intrusive::detail::bucket_traits_impl >::type>&) '
В файле, включенном в /usr/include/boost/intrusive/hashtable.hpp:30:0, из /usr/include/boost/intrusive/unordered_set.hpp:18, из t.cpp: 23:
/usr/include/boost/intrusive/detail/hashtable_node.hpp:80:8: note: 'constexpr boost::intrusive::detail::bucket_traits_impl >::type>::bucket_traits_impl(const boost::intrusive::detail::bucket_traits_impl >::type>&) 'неявно объявлено как удаленное, потому что' boost:: intrusive:: detail:: bucket_traits_impl>:: type> 'объявляет конструктор перемещения или оператор присваивания перемещения
Вот код, на который он ссылается, hashtable.hpp:227:
template<class BucketTraits>
bucket_plus_size(BOOST_FWD_REF(BucketTraits) b_traits)
: bucket_traits_(::boost::forward<BucketTraits>(b_traits))
{}
В Boost 1.47 это было:
bucket_plus_size(const bucket_traits &b_traits)
: bucket_traits_(b_traits)
{}
BOOST_FWD_REF(TYPE)
в моей системе определяется как TYPE &&
по умолчанию, но если BOOST_NO_RVALUE_REFERENCES
определяется тогда становится const TYPE &
, И если я определю это так, код скомпилируется!
Любые мысли о том, почему это? Это вина GCC, Boost, Fedora или моя?
1 ответ
Это похоже на ту же проблему, описанную на http://gcc.gnu.org/bugzilla/show_bug.cgi?id=53234
то есть Boost 1.48 предполагает старое поведение GCC 4.6, но GCC 4.7 был изменен для реализации правильной семантики C++11 в отношении неявно определенных конструкторов копирования / перемещения.