C++ 精神气:同一语法的不同切入点?

C++ 精神气:同一语法的不同切入点?,c++,parsing,boost,boost-spirit,boost-spirit-qi,C++,Parsing,Boost,Boost Spirit,Boost Spirit Qi,我有一个递归语法,希望从它的不同规则开始解析。如果不把同一个语法重写几遍,有可能吗 示例:我有json解析器: template <typename It, typename Skipper = qi::space_type> struct grammar : qi::grammar<It, value (), Skipper> { grammar () : grammar::base_type (value_) { using namespace qi;

我有一个递归语法,希望从它的不同规则开始解析。如果不把同一个语法重写几遍,有可能吗

示例:我有json解析器:

template <typename It, typename Skipper = qi::space_type>
struct grammar : qi::grammar<It, value (), Skipper>
{
  grammar () : grammar::base_type (value_)
  {
    using namespace qi;

    static auto const null_ = proto::deep_copy ("null" >> qi::attr (null {}));

    static auto const bool_ = proto::deep_copy (
      "true" >> qi::attr (true) | "false" >> qi::attr (false));

    static auto const text_ = proto::deep_copy (
      '"' >> qi::raw [*('\\' >> qi::char_ | ~qi::char_('"'))] >> '"');

    value_  = null_ | bool_ | text_ | double_ | object_ | array_;
    member_ = text_ >> ':' >> value_;
    object_ = '{' >> -(member_ % ',') >> '}';
    array_  = '[' >> -(value_ % ',') >> ']';

    BOOST_SPIRIT_DEBUG_NODES((value_)(member_)(object_)(array_))
  }

private:
  qi::rule<It, json:: value (), Skipper> value_;
  qi::rule<It, json::member (), Skipper> member_;
  qi::rule<It, json::object (), Skipper> object_;
  qi::rule<It, json:: array (), Skipper> array_;
};
模板
结构语法:qi::grammar
{
语法():语法::基本类型(值)
{
使用名称空间qi;
静态auto-const null=proto::deep_copy(“null”>>qi::attr(null{}));
静态自动常量bool\uu=proto::deep\u copy(
“true”>>qi::attr(true)|“false”>>qi::attr(false));
静态自动常量文本\=proto::deep\u复制(
“'>>qi::raw[*('\\'>>qi::char\u124; ~ qi::char\u124;('“)]>>”);
value|=null|bool|text|double|object|array|;
成员=文本:'>>值;
对象\='{'>>-(成员\%',')>'}';
数组\='['>>-(值\%',')>']';
BOOST_SPIRIT_DEBUG_节点((值_)(成员_)(对象_)(数组_))
}
私人:
qi::规则值;
qi::规则成员;
qi::规则对象;
qi::规则数组;
};

通常我需要将输入解析为json,但有时我需要将其解析为json数组或json对象。我可以不反复重写相同的语法,而这些语法之间的唯一区别是入口点吗?

我找到的最接近的解决方案是拆分语法ar分为基类和派生类,并在派生类中使用不同的启动规则。它不会大量复制源代码,但看起来仍然是一个解决方案

template <typename It, typename Data, typename Skipper = qi::space_type>
struct base : qi::grammar<It, Data (), Skipper>
{
  using jbase_type = base;

  template <typename Member>
  base (Member& member) : base::base_type (member)
  {
    using namespace qi;
    using namespace Json;

    value_  = null_ | bool_ | text_ | double_ | object_ | array_;
    member_ = text_ >> ':' >> value_;
    object_ = '{' >> -(member_ % ',') >> '}';
    array_  = '[' >> -(value_ % ',') >> ']';

    BOOST_SPIRIT_DEBUG_NODES((value_)(member_)(object_)(array_))
  }

protected:
  escaped_string_grammar<It> text_;

  qi::rule<It, Json:: Value (), Skipper> value_;
  qi::rule<It, Json::Member (), Skipper> member_;
  qi::rule<It, Json::Object (), Skipper> object_;
  qi::rule<It, Json:: Array (), Skipper> array_;
};

//++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++//
template <typename It, typename Skipper = qi::space_type>
struct value : base<It, Json::Value, Skipper>
{
  value () : value::jbase_type (value::jbase_type::value_) {}
};

//++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++//
template <typename It, typename Skipper = qi::space_type>
struct array : base<It, Json::Array, Skipper>
{
  array () : array::jbase_type (array::jbase_type::array_) {}
};

//++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++//
template <typename It, typename Skipper = qi::space_type>
struct object : base<It, Json::Object, Skipper>
{
  object () : object::jbase_type (object::jbase_type::object_) {}
};
模板
结构基:qi::grammar
{
使用jbase_type=base;
模板
基本(成员和成员):基本::基本类型(成员)
{
使用名称空间qi;
使用名称空间Json;
value|=null|bool|text|double|object|array|;
成员=文本:'>>值;
对象\='{'>>-(成员\%',')>'}';
数组\='['>>-(值\%',')>']';
BOOST_SPIRIT_DEBUG_节点((值_)(成员_)(对象_)(数组_))
}
受保护的:
转义字符串语法文本;
qi::规则值;
qi::规则成员;
qi::规则对象;
qi::规则数组;
};
//++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++//
模板
结构值:base
{
value():value::jbase_类型(value::jbase_类型::value_){
};
//++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++//
模板
结构数组:基
{
数组():数组::jbase_类型(数组::jbase_类型::数组{}
};
//++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++//
模板
结构对象:基
{
对象():对象::jbase_类型(对象::jbase_类型::对象{}
};