【问题标题】:Returning multiple data types from Boost::spirit parse从 Boost::spirit 解析返回多种数据类型
【发布时间】:2015-02-24 23:37:03
【问题描述】:

我想解析大约 5-10 种不同的消息类型,它们共享一种通用格式(例如 JSON),但每种都有需要验证的特定字段。每条消息最终都应该被解析成一个自定义类/结构,该类/结构的类型不需要任何类型的转换(例如,一个字段是一个 int 而不是一个变体/元组)。我看到了解决问题的两种方法:

  1. 为每个特定消息编写语法,处理消息格式(在本例中为 JSON 样板)的验证和字段内容的验证,返回真正自定义的结构

  2. 编写仅验证结构(仅 JSON 规则)并返回更通用的对象(具有变体/元组等字段)并在更高级别验证/转换为自定义结构的语法(铸造和检查各种变体字段)

我认为这些是各自的优缺点:

1 的优点:

  • 所有验证都在 boost::spirit 中完成
  • Karma 生成器(如果已编写)看起来像现有的精神解析代码

1 的缺点:

  • 必须为将来可能发明的每种新消息类型编写和维护新语法(并且精神语法不直观)

2 的优点:

  • 复杂的精神代码只写一次,很少接触

2 的缺点:

  • 通用消息对象的验证和翻译将是精神应该首先消除的混乱代码

哪种方法更可取?有没有第三种方法可以用一种语法解析成多种类型?

以下是一些示例消息以及它们最终应驻留在的类:

{"messageType": "messageTypeA", "numberParam": 1}
{"messageType": "messageTypeB", "stringParam": "Test"}

class MessageTypeA
{
public:
    double numberParam;
};

class MessageTypeB
{
public:
    std::string stringParam;
};

【问题讨论】:

    标签: c++ boost qi


    【解决方案1】:

    我认为这个问题与最近的答案非常接近,而我正是这样做的:我回答了 两个 答案:

    1. Answer #1 采取通才的方法,只是根据特定的“方案”进行解释
    2. Answer #2 采用临时方法,OP 认为这种方法更容易

    我的投票是第一个选项,因为

    • “复杂的代码只需要编写和测试一次,而且很少接触”在我的经验中胜过其他因素,
    • 事实上,语法极大地受益于职责分离和保持 AST 真正接近自然规则属性
    • 我已将 JSON 后端(OData、Edm、版本、元数据级别)的多种“风格”写入我的融合适应类型(使用融合“反射”)。这些全部共享同一个解析器/生成器。

    即使是链接问题中的 OP,后来似乎也需要我的第一个答案已经提供的灵活性:

    哦,好吧。我很惊讶您当时接受了这个答案,因为另一个答案完全相同,只是它确实接受并忽略了“其他”JSON内容。您是否错过了定义extract_from 的更新?它使用完全相同的数据结构——你在问题中建议的那个。– sehe Jan 4 at 16:41

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多