如何用std :: optional 在C ++中键入来解析json文件?

问题描述 投票:0回答:1

我如何解析此文件中的输入json,尤其是对于secondary属性?

https://github.com/smogon/pokemon-showdown/blob/master/data/moves.js

它们是optionalvariant的类型组成。

尽管只有完整的示例可以更清楚地揭示问题,但是最小的起点示例就是这个:

    [
      {},
      {
        "secondary": false
      },
      {

        "secondary": {
          "chance": 10,
          "boosts": {
            "spd": -1
          }
        }
      },
      {
        "secondary": {
          "chance": 30,
          "volatileStatus": "flinch"
        }
      },
      {
        "secondary": {
          "chance": 30
        }
      },
      {
        "secondary": {
          "chance": 10,
          "self": {
            "boosts": {
              "atk": 1,
              "def": 1,
              "spa": 1,
              "spd": 1,
              "spe": 1
            }
          }
        }
      },
      {
        "secondary": {
          "chance": 10,
          "status": "brn"
        }
      },
      {
        "secondary": {
          "chance": 50,
          "self": {
            "boosts": {
              "def": 2
            }
          }
        }
      },
      {
        "secondary": {
          "chance": 100,
          "self": {}
        }
      },
      {
        "secondary": {
          "chance": 50,
          "boosts": {
            "accuracy": -1
          }
        }
      }
    ]

[为方便起见,您可以将此代码段附加到js文件的末尾并使用node move.js运行它。两个有效的json文件将保存到磁盘。一个是json对象的列表,另一个是带有字符串作为键的对象。

var fs = require('fs');
fs.writeFile("moves_object.json", JSON.stringify(BattleMovedex), function(err) {}); // 1. save a json object with string key

var jsonList = []
for (var key of Object.keys(BattleMovedex)) {
    jsonList.push(BattleMovedex[key]);
}
fs.writeFile("moves.json", JSON.stringify(jsonList), function(err) { // 2. save as a list of json object
    if (err) {
        console.log(err);
    }
});

在c ++(17/20)中,这里有以前的尝试:https://github.com/nlohmann/json/issues/1281

https://github.com/nlohmann/json/issues/1910

https://github.com/nlohmann/json/issues/1261

这里是一个样板处理简单的可选字段,您可以从以下开始:

struct Boosts {
    optional<int> atk;
    optional<int> def;
};

struct Self {
    optional<Boosts> boosts;
};
struct Secondary {
    optional<int> chance;
    optional<string> volatileStatus;
    optional<Boosts> boosts;
    optional<Self> self;
    optional<string> status;
};

struct move_t {
    int num;
    variant<bool, int> accuracy;
    int basePower;
    string category;
    optional<string> desc = std::nullopt;
    string shortDesc;
    string id;
    string name;
    optional<variant<bool, Secondary>> secondary;

};
c++ json optional variant rapidjson
1个回答
0
投票

我宁愿(ab)将'std :: monostate'用作'std :: variant'的第一类型arg,而不是在'std :: variant'上使用'std :: optional'。如果变量保持单态,则表示为空变量。顺便说一下,为什么在'boost :: property_tree'可用时重新发明轮子?

https://www.boost.org/doc/libs/1_72_0/doc/html/property_tree.html

© www.soinside.com 2019 - 2024. All rights reserved.