я использую boost 1.53
а также GCC 4.1.2
, Я пытался использовать повышение unordered_map
в некоторых тестах (документация говорит, что он должен работать с общей памятью), но я не могу скомпилировать свой код. С interprocess::map
вместо неупорядоченного все ок.
Определения типов:
typedef boost::interprocess::allocator<char, SegmentManager> CharAllocator;
typedef boost::interprocess::basic_string<char, std::char_traits<char>, CharAllocator> ShmString;
typedef ShmString HashKeyType;
//ComplexType is a wrapper for internal interprocess::map
typedef ComplexType HashMappedType;
typedef std::pair<const ShmString, ComplexType> HashValueType;
typedef boost::interprocess::allocator<HashValueType,
boost::interprocess::managed_shared_memory::segment_manager> HashMemAllocator;
typedef boost::unordered_map
< HashKeyType , HashMappedType
, boost::hash<HashKeyType> ,std::equal_to<HashKeyType>
, HashMemAllocator>
TestHashMap;
Распределение:
boost::interprocess::managed_shared_memory segment( boost::interprocess::open_or_create, "MySharedMemory", 65536);
thm_ = segment.construct<TestHashMap>("TestHashMap")
(3, boost::hash<ShmString>(), std::equal_to<ShmString>()
, segment.get_allocator<HashValueType>());
Использование:
boost::interprocess::managed_shared_memory segment( boost::interprocess::open_only, "MySharedMemory");
ShmString str("123.345", segment.get_allocator<ShmString>());
ComplexType th("MySharedMemory");
HashValueType value(str, th);
thm_->insert(value);
И вот вывод некоторых ошибок:
../boost/include/boost/unordered/detail/allocate.hpp: In instantiation of 'boost::unordered::detail::allocator_traits<boost::interprocess::allocator<boost::unordered::detail::ptr_node<std::pair<const boost::container::basic_string<char, std::char_traits<char>, boost::interprocess::allocator<char, boost::interprocess::segment_manager<char, boost::interprocess::rbtree_best_fit<boost::interprocess::mutex_family, boost::interprocess::offset_ptr<void, long int, long unsigned int, 0u>, 0ul>, boost::interprocess::iset_index> > >, TINHolderShared> >, boost::interprocess::segment_manager<char, boost::interprocess::rbtree_best_fit<boost::interprocess::mutex_family, boost::interprocess::offset_ptr<void, long int, long unsigned int, 0u>, 0ul>, boost::interprocess::iset_index> > >::pointer_to_other<const boost::unordered::detail::ptr_node<std::pair<const boost::container::basic_string<char, std::char_traits<char>, boost::interprocess::allocator<char, boost::interprocess::segment_manager<char, boost::interprocess::rbtree_best_fit<boost::interprocess::mutex_family, boost::interprocess::offset_ptr<void, long int, long unsigned int, 0u>, 0ul>, boost::interprocess::iset_index> > >, TINHolderShared> > >':
../boost/include/boost/unordered/detail/allocate.hpp:527: instantiated from 'boost::unordered::detail::allocator_traits<boost::interprocess::allocator<boost::unordered::detail::ptr_node<std::pair<const boost::container::basic_string<char, std::char_traits<char>, boost::interprocess::allocator<char, boost::interprocess::segment_manager<char, boost::interprocess::rbtree_best_fit<boost::interprocess::mutex_family, boost::interprocess::offset_ptr<void, long int, long unsigned int, 0u>, 0ul>, boost::interprocess::iset_index> > >, TINHolderShared> >, boost::interprocess::segment_manager<char, boost::interprocess::rbtree_best_fit<boost::interprocess::mutex_family, boost::interprocess::offset_ptr<void, long int, long unsigned int, 0u>, 0ul>, boost::interprocess::iset_index> > >'
../boost/include/boost/unordered/detail/unique.hpp:114: instantiated from 'boost::unordered::detail::pick_node<boost::interprocess::allocator<std::pair<const boost::container::basic_string<char, std::char_traits<char>, boost::interprocess::allocator<char, boost::interprocess::segment_manager<char, boost::interprocess::rbtree_best_fit<boost::interprocess::mutex_family, boost::interprocess::offset_ptr<void, long int, long unsigned int, 0u>, 0ul>, boost::interprocess::iset_index> > >, TINHolderShared>, boost::interprocess::segment_manager<char, boost::interprocess::rbtree_best_fit<boost::interprocess::mutex_family, boost::interprocess::offset_ptr<void, long int, long unsigned int, 0u>, 0ul>, boost::interprocess::iset_index> >, std::pair<const boost::container::basic_string<char, std::char_traits<char>, boost::interprocess::allocator<char, boost::interprocess::segment_manager<char, boost::interprocess::rbtree_best_fit<boost::interprocess::mutex_family, boost::interprocess::offset_ptr<void, long int, long unsigned int, 0u>, 0ul>, boost::interprocess::iset_index> > >, TINHolderShared> >'
../boost/include/boost/unordered/detail/unique.hpp:158: instantiated from 'boost::unordered::detail::map<boost::interprocess::allocator<std::pair<const boost::container::basic_string<char, std::char_traits<char>, boost::interprocess::allocator<char, boost::interprocess::segment_manager<char, boost::interprocess::rbtree_best_fit<boost::interprocess::mutex_family, boost::interprocess::offset_ptr<void, long int, long unsigned int, 0u>, 0ul>, boost::interprocess::iset_index> > >, TINHolderShared>, boost::interprocess::segment_manager<char, boost::interprocess::rbtree_best_fit<boost::interprocess::mutex_family, boost::interprocess::offset_ptr<void, long int, long unsigned int, 0u>, 0ul>, boost::interprocess::iset_index> >, boost::container::basic_string<char, std::char_traits<char>, boost::interprocess::allocator<char, boost::interprocess::segment_manager<char, boost::interprocess::rbtree_best_fit<boost::interprocess::mutex_family, boost::interprocess::offset_ptr<void, long int, long unsigned int, 0u>, 0ul>, boost::interprocess::iset_index> > >, TINHolderShared, boost::hash<boost::container::basic_string<char, std::char_traits<char>, boost::interprocess::allocator<char, boost::interprocess::segment_manager<char, boost::interprocess::rbtree_best_fit<boost::interprocess::mutex_family, boost::interprocess::offset_ptr<void, long int, long unsigned int, 0u>, 0ul>, boost::interprocess::iset_index> > > >, std::equal_to<boost::container::basic_string<char, std::char_traits<char>, boost::interprocess::allocator<char, boost::interprocess::segment_manager<char, boost::interprocess::rbtree_best_fit<boost::interprocess::mutex_family, boost::interprocess::offset_ptr<void, long int, long unsigned int, 0u>, 0ul>, boost::interprocess::iset_index> > > > >'
../boost/include/boost/unordered/unordered_map.hpp:59: instantiated from 'boost::unordered::unordered_map<boost::container::basic_string<char, std::char_traits<char>, boost::interprocess::allocator<char, boost::interprocess::segment_manager<char, boost::interprocess::rbtree_best_fit<boost::interprocess::mutex_family, boost::interprocess::offset_ptr<void, long int, long unsigned int, 0u>, 0ul>, boost::interprocess::iset_index> > >, TINHolderShared, boost::hash<boost::container::basic_string<char, std::char_traits<char>, boost::interprocess::allocator<char, boost::interprocess::segment_manager<char, boost::interprocess::rbtree_best_fit<boost::interprocess::mutex_family, boost::interprocess::offset_ptr<void, long int, long unsigned int, 0u>, 0ul>, boost::interprocess::iset_index> > > >, std::equal_to<boost::container::basic_string<char, std::char_traits<char>, boost::interprocess::allocator<char, boost::interprocess::segment_manager<char, boost::interprocess::rbtree_best_fit<boost::interprocess::mutex_family, boost::interprocess::offset_ptr<void, long int, long unsigned int, 0u>, 0ul>, boost::interprocess::iset_index> > > >, boost::interprocess::allocator<std::pair<const boost::container::basic_string<char, std::char_traits<char>, boost::interprocess::allocator<char, boost::interprocess::segment_manager<char, boost::interprocess::rbtree_best_fit<boost::interprocess::mutex_family, boost::interprocess::offset_ptr<void, long int, long unsigned int, 0u>, 0ul>, boost::interprocess::iset_index> > >, TINHolderShared>, boost::interprocess::segment_manager<char, boost::interprocess::rbtree_best_fit<boost::interprocess::mutex_family, boost::interprocess::offset_ptr<void, long int, long unsigned int, 0u>, 0ul>, boost::interprocess::iset_index> > >'
utest/THUnitTests.cc:96: instantiated from here
../boost/include/boost/unordered/detail/allocate.hpp:523: error: ambiguous class template instantiation for 'struct boost::pointer_to_other<boost::interprocess::offset_ptr<boost::unordered::detail::ptr_node<std::pair<const boost::container::basic_string<char, std::char_traits<char>, boost::interprocess::allocator<char, boost::interprocess::segment_manager<char, boost::interprocess::rbtree_best_fit<boost::interprocess::mutex_family, boost::interprocess::offset_ptr<void, long int, long unsigned int, 0u>, 0ul>, boost::interprocess::iset_index> > >, TINHolderShared> >, long int, long unsigned int, 0u>, const boost::unordered::detail::ptr_node<std::pair<const boost::container::basic_string<char, std::char_traits<char>, boost::interprocess::allocator<char, boost::interprocess::segment_manager<char, boost::interprocess::rbtree_best_fit<boost::interprocess::mutex_family, boost::interprocess::offset_ptr<void, long int, long unsigned int, 0u>, 0ul>, boost::interprocess::iset_index> > >, TINHolderShared> > >'
../boost/include/boost/interprocess/offset_ptr.hpp:721: error: candidates are: struct boost::pointer_to_other<boost::interprocess::offset_ptr<T1, P1, O1, A1>, U>
../boost/include/boost/pointer_to_other.hpp:29: error: struct boost::pointer_to_other<Sp<T>, U>
../boost/include/boost/pointer_to_other.hpp:36: error: struct boost::pointer_to_other<Sp<T, T2>, U>
../boost/include/boost/pointer_to_other.hpp:43: error: struct boost::pointer_to_other<Sp<T, T2, T3>, U>
Я не уверен, что проблема в моем коде, или из-за старой версии компилятора.
Если проблема с компилятором, то можно ли это исправить с помощью более новой версии boost? (я не могу обновить свой GCC). Или, может быть, есть некоторые реализации хеш-таблицы, которые совместимы с разделяемой памятью и моим компилятором?
Вот исправленная версия.
Я просто попытался сделать это самодостаточным в соответствии с наводящими комментариями. И это работает.
Надеюсь, это поможет в любом случае:
#include <boost/interprocess/managed_shared_memory.hpp>
#include <boost/interprocess/containers/string.hpp>
#include <boost/interprocess/containers/map.hpp>
#include <boost/unordered_map.hpp>
namespace bip = boost::interprocess;
// ShmString is boost::interprocess::basic_string
typedef bip::allocator<char, bip::managed_shared_memory::segment_manager> CharAllocator;
typedef bip::basic_string<char, std::char_traits<char>, CharAllocator> ShmString;
typedef ShmString HashKeyType;
// ComplexType is a wrapper for internal interprocess::map
struct ComplexType {
typedef bip::allocator<std::pair<int const, int>, bip::managed_shared_memory::segment_manager> Alloc;
typedef bip::map<int, int, std::less<int>, Alloc> Map;
template <typename Alloc2>
ComplexType(std::string, Alloc2 const& alloc = {}) : map(alloc) {}
Map map;
};
typedef ComplexType HashMappedType;
typedef std::pair<const ShmString, ComplexType> HashValueType;
typedef bip::allocator<HashValueType, bip::managed_shared_memory::segment_manager> HashMemAllocator;
typedef boost::unordered_map<HashKeyType, HashMappedType, boost::hash<HashKeyType>, std::equal_to<HashKeyType>, HashMemAllocator>
TestHashMap;
int main()
{
// Allocation:
{
bip::managed_shared_memory segment(bip::open_or_create, "MySharedMemory", 65536);
auto thm_ = segment.construct<TestHashMap>("TestHashMap")(3, boost::hash<ShmString>(), std::equal_to<ShmString>(),
segment.get_allocator<HashValueType>());
}
// Usage:
bip::managed_shared_memory segment(bip::open_only, "MySharedMemory");
auto thm_ = segment.construct<TestHashMap>("TestHashMap")(3, boost::hash<ShmString>(), std::equal_to<ShmString>(), segment.get_allocator<HashValueType>());
ShmString str("123.345", segment.get_allocator<ShmString>());
ComplexType th("MySharedMemory", segment.get_segment_manager());
HashValueType value(str, th);
thm_->insert(value);
}