使用boost :: spirit :: karma输出boost :: variant类型

时间:2013-08-06 19:27:56

标签: boost boost-spirit boost-variant boost-spirit-karma

我正在尝试输出参数,它们可以是单个参数,也可以是参数矢量。以下代码不是我想要它做的:

#include <iostream>
#include <string>
#include <boost/variant.hpp>
#include <boost/spirit/include/karma.hpp>
namespace karma = boost::spirit::karma;

typedef std::vector<int> ParameterList;
typedef boost::variant<int, ParameterList> Parameter;

main()
{
    using karma::int_;
    using karma::eol;
    using karma::lit;

    std::string generated;
    std::back_insert_iterator<std::string> sink(generated);

    karma::rule<std::back_insert_iterator<std::string>, ParameterList()> parameterListRule = int_ % lit(", ");
    karma::rule<std::back_insert_iterator<std::string>, Parameter()> parameterRule = (int_ | parameterListRule) << eol;

    karma::generate(sink, parameterRule, 1); // Works
    karma::generate(sink, parameterRule, ParameterList{1, 2}); // Doesn't work
    std::cout << generated << "\n";
}

(真正的代码有其他类型的参数,不仅仅是int,我不能只把一切都变成ParameterList。)

我不太明白如何使这项工作,特别是因为使用boost :: spirit :: qi,解析的类似结构对我来说很好。

1 个答案:

答案 0 :(得分:3)

在第二次调用中,您没有在生成器中放置变体,但规则需要一个。

#include <iostream>
#include <string>
#include <boost/variant.hpp>
#include <boost/spirit/include/karma.hpp>
namespace karma = boost::spirit::karma;

typedef std::vector<int> ParameterList;
typedef boost::variant<int, ParameterList> Parameter;

main()
{
    using karma::int_;
    using karma::eol;
    using karma::lit;

    std::string generated;
    std::back_insert_iterator<std::string> sink(generated);

    karma::rule<std::back_insert_iterator<std::string>, ParameterList()> parameterListRule = int_ % lit(", ");
    karma::rule<std::back_insert_iterator<std::string>, Parameter()> parameterRule = (int_ | parameterListRule) << eol;

    karma::generate(sink, parameterRule, 1); // Works
    // use variant here:
    Parameter test(ParameterList{1, 2});
    karma::generate(sink, parameterRule, test);
    std::cout << generated << "\n";
}