как увеличить количество типов, которые могут обрабатываться boost:: variant

Я разрабатываю парсер для языка verilog, и у одного из правил есть 25 компонентов, для которых мне нужен большой boost::variant:

typedef boost::variant<
 shared_ptr<T_module_item__port_declaration>
 ,  shared_ptr<T_module_item__generate_region>
 ,  shared_ptr<T_module_item__specify_block>
 ,  shared_ptr<T_module_item__parameter_declaration>
 ,  shared_ptr<T_module_item__specparam_declaration>
 ,  shared_ptr<T_module_item__net_declaration>
 ,  shared_ptr<T_module_item__reg_declaration>
 ,  shared_ptr<T_module_item__integer_declaration>
 ,  shared_ptr<T_module_item__real_declaration>
 ,  shared_ptr<T_module_item__time_declaration>
 ,  shared_ptr<T_module_item__realtime_declaration>
 ,  shared_ptr<T_module_item__event_declaration>
 ,  shared_ptr<T_module_item__genvar_declaration>
 ,  shared_ptr<T_module_item__task_declaration>
 ,  shared_ptr<T_module_item__function_declaration>
 ,  shared_ptr<T_module_item__local_parameter_declaration>
 ,  shared_ptr<T_module_item__parameter_override>
 ,  shared_ptr<T_module_item__continuous_assign>
 ,  shared_ptr<T_module_item__gate_instantiation>
 ,  shared_ptr<T_module_item__udp_instantiation>
 ,  shared_ptr<T_module_item__module_instantiation>
 ,  shared_ptr<T_module_item__initial_construct>
 ,  shared_ptr<T_module_item__always_construct>
 ,  shared_ptr<T_module_item__loop_generate_construct>
 ,  shared_ptr<T_module_item__conditional_generate_construct>
 > module_item ; 

но g++ жалуется, что вариант boost::может содержать не более 20 типов.

verilogast.h|1129 col 2| error: wrong number of template arguments (25, should be 20)
||   > module_item ; 
||   ^
/usr/include/boost/variant/variant_fwd.hpp|213 col 53| error: provided for ‘template<class T0, class T1, class T2, class T3, class T4, class T5, class T6, class T7, class T8, class T9, class T10, class T11, class T12, class T13, class T14, class T15, class T16, class T17, class T18, class T19> class boost::variant’
||  template < BOOST_VARIANT_AUX_DECLARE_PARAMS > class variant;

Я пытаюсь переопределить BOOST_VARIANT_LIMIT_TYPES на большее значение:

#define BOOST_VARIANT_LIMIT_TYPES 30
#include<boost/variant.hpp>

но ошибка все равно есть,

2 ответов


ошибки в clang++ и g++ в режиме c++98 (что вы, кажется, получаете) довольно короткие (и, к сожалению, бесполезны). В c++11 ошибка намного больше и выявить ключевую проблему:

ошибка: слишком много аргументов шаблона для шаблона класса "list"
typedef имя типа mpl:: list::type тип;

Если вы посмотрите в импульс.Документация MPL вы можете видеть, что нужно добавить:

#define BOOST_MPL_CFG_NO_PREPROCESSED_HEADERS
#define BOOST_MPL_LIMIT_LIST_SIZE 30

вы можете сделать только список размер 30, 40 или 50 по умолчанию, если вы хотите больше вам придется создавать пользовательские заголовки.

бег на Coliru


Я также наткнулся на ту же проблему. К сожалению, я не могу использовать решение выше, так как я зависим от других библиотек, уже использующих boost-variant С #define BOOST_MPL_LIMIT_LIST_SIZE 20. Перекомпиляция boost-variant библиотеки waws также не являются желаемым решением для меня.

следовательно, я разработал обходной путь для моей проблемы. Следующий код иллюстрирует идею этого обходного пути с 39 типами.

typedef boost::variant<
    A<20>,A<21>,A<22>,A<23>,A<24>,A<25>,A<26>,A<27>,A<28>,A<29>,A<30>,A<31>,A<32>,A<33>,A<34>,A<35>,A<36>,A<37>,A<38>,A<39>
> NextVar;

typedef boost::variant<
    A<1>,A<2>,A<3>,A<4>,A<5>,A<6>,A<7>,A<8>,A<9>,A<10>,A<11>,A<12>,A<13>,A<14>,A<15>,A<16>,A<17>,A<18>,A<19>,NextVar
> TVar;

struct PrintVisitor : public boost::static_visitor<std::string> {
    result_type operator()(const NextVar& n) {
        return n.apply_visitor(*this);
    }

    template<int T>
    result_type operator()(const A<T>& a)  {
        return std::to_string(a.value);
    }
};

int main(int argc, char **args) {
    TVar x = A<35>(); // Implicit conversion! Great!
    PrintVisitor v;
    std::cout << x.apply_visitor(v) << std::endl;
}

решение просто создает список boost-variant типы (аналогично линейному списку).