編輯:我發現並編寫了一個解決方案,但我沒有回答這個問題,因爲我的解決方案可能仍然不理想。從任意地圖獲取指向mapped_type的指針或引用
我正在寫一個小型庫,用於在地圖上執行例程,但我在設計一組類模板時會遇到麻煩,這些模板會讓我得到一個指針或引用(取決於地圖的value_type的second_type )映射到mapped_type,而不管映射的類型(例如std :: map,boost :: ptr_map)。
爲了進一步闡述,我列出了一些輸入類型和所需的輸出類型。
Case Input Type Output Type
A std::map<int, std::map<int, int> > std::map<int, int>&
B std::map<int, boost::ptr_map<int, int> > boost::ptr_map<int, int>&
C boost::ptr_map<int, std::map<int, int> > std::map<int, int>* const
D std::map<int, std::map<int, int> >* std::map<int, int>&
E std::map<int, boost::ptr_map<int, int> >* boost::ptr_map<int, int>&
F boost::ptr_map<int, std::map<int, int> >* std::map<int, int>* const
我的代碼經過的情況下A,B,d和E,但未能對案件C和F這裏是我到目前爲止所。
template <class Map>
struct map_utils
{
template <class K>
static typename
boost::remove_pointer<
typename Map::value_type
>::type::second_type&
get(Map& m, const K k)
{
return m[k];
}
template <class K>
static typename
boost::remove_pointer<
typename Map::value_type
>::type::second_type&
get(const Map& m, const K k)
{
return const_cast<Map&>(m)[k];
}
};
template <class Map>
struct map_utils<Map*>
{
template <class T>
static typename
boost::remove_pointer<
typename Map::value_type
>::type::second_type&
get(Map* m, const T t)
{
return (*m)[t];
}
template <class T>
static typename
boost::remove_pointer<
typename Map::value_type
>::type::second_type&
get(const Map* m, const T t)
{
return const_cast<Map*>(m)->operator[](t);
}
};
我想使用boost :: MPL要做到這一點,這是我到目前爲止已經熟了起來,但我得到使用的代碼的兩個版本相同的錯誤。
錯誤。
error: invalid initialization of reference of type ‘std::map<int, double>* const&’ from expression of type ‘boost::ptr_container_detail::reversible_ptr_container<boost::ptr_container_detail::map_config<std::map<int, double>, std::map<int, void*, std::less<int>, std::allocator<std::pair<const int, void*> > >, true>, boost::heap_clone_allocator>::Ty_’
修改後的結構專用於處理不是指向映射的指針的l值。
template <class K>
static typename boost::remove_pointer<
typename Map::mapped_type
>::type&
get(Map& m, const K k)
{
return m[k];
}
只需要方法的身體在改變:
template <class K>
static typename
boost::mpl::if_<
boost::is_pointer<
typename boost::remove_pointer<
typename Map::value_type
>::type::second_type
>,
typename boost::remove_pointer<
typename boost::remove_const<
typename Map::value_type
>::type
>::type::second_type,
typename boost::remove_pointer<
typename Map::value_type
>::type::second_type&
>::type
get(Map& m, const K k)
{
return m[k];
}
糟糕,我的壞 - 現在已經修好了。 –
您的解決方案比我的優雅得多 - 我沒有想過使用模板參數來表示鍵和值類型。 –
爲了適應任意的地圖類型,你可以在'class Whatever'的非特化版本中將'class Map'更改爲'template Map'。 –