2016-04-29 7 views
2

Я пытаюсь использовать boost::graph, у которого есть enum внутри его связанного свойства вершин. Проблема начинается, когда я пытаюсь использовать свойство bundled для boost :: dynamic_property. Похоже, я не могу получить правильную специализацию шаблонов для boost :: lexical_cast, чтобы распознать тип.specializing boost :: lexical_cast для перечислений в boost :: property_maps

#include <string> 
#include <iostream> 
#include <boost/lexical_cast.hpp> 
#include <boost/graph/adjacency_list.hpp> 
#include <boost/property_map/dynamic_property_map.hpp> 

enum MyEnum { A, B, C }; 

namespace boost{ 
    template<> 
    std::string lexical_cast(const MyEnum & m) 
    { 
     return std::to_string(int(m)); 
    } 
} /* boost */ 

struct EnumWrapper 
{ 
    MyEnum e; 

    EnumWrapper() = default; 
    EnumWrapper(MyEnum e) : e{e} 
    {} 
}; 

int main() 
{ 
    using namespace boost; 

    // This works 
    MyEnum e{MyEnum::B}; 
    std::cout << lexical_cast<std::string>(e) << std::endl; 

    // This doesn't compile 
    adjacency_list<vecS, vecS, directedS, EnumWrapper> graph; 
    dynamic_properties dp; 
    dp.property("test", get(&EnumWrapper::e, graph)); 

    return 0; 
} 

Если я пытаюсь писать enum непосредственно, все работает отлично. Когда попытка поставить его в динамическом свойстве, появляется следующее сообщение об ошибке:

In file included from /usr/include/boost/iterator/iterator_categories.hpp:22:0, 
       from /usr/include/boost/iterator/iterator_facade.hpp:14, 
       from /usr/include/boost/range/iterator_range_core.hpp:27, 
       from /usr/include/boost/lexical_cast.hpp:30, 
       from main.cpp:3: 
/usr/include/boost/lexical_cast/detail/converter_lexical.hpp: In instantiation of ‘struct boost::detail::deduce_target_char_impl<boost::detail::deduce_character_type_later<MyEnum> >’: 
/usr/include/boost/lexical_cast/detail/converter_lexical.hpp:270:89: required from ‘struct boost::detail::deduce_target_char<MyEnum>’ 
/usr/include/boost/lexical_cast/detail/converter_lexical.hpp:407:92: required from ‘struct boost::detail::lexical_cast_stream_traits<std::__cxx11::basic_string<char>, MyEnum>’ 
/usr/include/boost/lexical_cast/detail/converter_lexical.hpp:468:15: required from ‘struct boost::detail::lexical_converter_impl<MyEnum, std::__cxx11::basic_string<char> >’ 
/usr/include/boost/lexical_cast/try_lexical_convert.hpp:181:44: required from ‘bool boost::conversion::detail::try_lexical_convert(const Source&, Target&) [with Target = MyEnum; Source = std::__cxx11::basic_string<char>]’ 
/usr/include/boost/lexical_cast.hpp:41:60: required from ‘Target boost::lexical_cast(const Source&) [with Target = MyEnum; Source = std::__cxx11::basic_string<char>]’ 
/usr/include/boost/property_map/dynamic_property_map.hpp:44:38: required from ‘Value boost::detail::read_value(const string&) [with Value = MyEnum; std::__cxx11::string = std::__cxx11::basic_string<char>]’ 
/usr/include/boost/property_map/dynamic_property_map.hpp:158:64: required from ‘void boost::detail::dynamic_property_map_adaptor<PropertyMap>::do_put(const boost::any&, const boost::any&, mpl_::bool_<true>) [with PropertyMap = boost::vec_adj_list_vertex_property_map<boost::adjacency_list<boost::vecS, boost::vecS, boost::directedS, EnumWrapper>, boost::adjacency_list<boost::vecS, boost::vecS, boost::directedS, EnumWrapper>*, MyEnum, MyEnum&, MyEnum EnumWrapper::*>]’ 
/usr/include/boost/property_map/dynamic_property_map.hpp:186:11: required from ‘void boost::detail::dynamic_property_map_adaptor<PropertyMap>::put(const boost::any&, const boost::any&) [with PropertyMap = boost::vec_adj_list_vertex_property_map<boost::adjacency_list<boost::vecS, boost::vecS, boost::directedS, EnumWrapper>, boost::adjacency_list<boost::vecS, boost::vecS, boost::directedS, EnumWrapper>*, MyEnum, MyEnum&, MyEnum EnumWrapper::*>]’ 
main.cpp:40:1: required from here 
/usr/include/boost/lexical_cast/detail/converter_lexical.hpp:243:13: error: static assertion failed: Target type is neither std::istream`able nor std::wistream`able 
      BOOST_STATIC_ASSERT_MSG((result_t::value || boost::has_right_shift<std::basic_istream<wchar_t>, T >::value), 

Линия Target type is neither std::istreamable nor std::wistreamable подсказывает мне, что lexical_cast не специализирована правильно. Тем не менее, использование лексического литья напрямую работает очень хорошо.

+0

'Target = MyEnum; Source = std :: __ cxx11 :: basic_string '. Boost пытается преобразовать * из * 'string' * в *' MyEnum'; вы только указали обратное направление. – ecatmur

ответ

2

Target = MyEnum; Source = std::__cxx11::basic_string<char>. Boost пытается преобразовать отstringкMyEnum; вы только указали обратное направление.

Вы должны обеспечить преобразование изstringкMyEnum:

namespace boost{ 
    template<> 
    MyEnum lexical_cast(const std::string & s) { 
     return MyEnum::A; // for example 
    } 
} /* boost */ 

Example.

+0

хорошо, так много для небольших изменений в сообщении об ошибке. Я сначала исправил другое направление и не понял, что теперь «Целевая» и «Источник» были переключены. – Slizzered

 Смежные вопросы

  • Нет связанных вопросов^_^