4.8 C++ Boost 应用JSON解析库

本文涉及的产品
公共DNS(含HTTPDNS解析),每月1000万次HTTP解析
全局流量管理 GTM,标准版 1个月
云解析 DNS,旗舰版 1个月
简介: property_tree 是 Boost 库中的一个头文件库,用于处理和解析基于 XML、Json 或者 INFO 格式的数据。 property_tree 可以提供一个轻量级的、灵活的、基于二叉数的通用容器,可以处理包括简单值(如 int、float)和复杂数据结构(如结构体和嵌套容器)在内的各种数据类型。它可以解析数据文件到内存中,然后通过迭代器访问它们。

property_tree 是 Boost 库中的一个头文件库,用于处理和解析基于 XML、Json 或者 INFO 格式的数据。 property_tree 可以提供一个轻量级的、灵活的、基于二叉数的通用容器,可以处理包括简单值(如 int、float)和复杂数据结构(如结构体和嵌套容器)在内的各种数据类型。它可以解析数据文件到内存中,然后通过迭代器访问它们。

在 Boost 库中,property_tree 通常与 boost/property_tree/xml_parser.hpp、boost/property_tree/json_parser.hpp 或 boost/property_tree/info_parser.hpp 文件一起使用。这些文件分别提供了将 XML、JSON 或 INFO 格式数据解析为 property_tree 结构的功能。

首先我们需要自行创建一个测试config.json文件,后期的所有案例演示及应用都需要这个库的支持。

{
   
    "username": "lyshark",
    "age": 24,
  "get_dict": {
    "username": "lyshark" },
    "get_list": [ 1, 2, 3, 4, 5, 6, 7, 8, 9, 10 ],
    "user_data":
     [
        [ "192.168.1.1", "root", "123456" ],
        [ "192.168.1.2", "admin", "123456" ],
        [ "192.168.1.3", "mysql", "123456" ]
    ],

    "user_dict":
     [
        {
    "uid": 1001, "uname": "admin" },
        {
    "uid": 1002, "uname": "lyshark" },
        {
    "uid": 1003, "uname": "root" }
    ],

    "get_root":
     [
        {
   
            "firstName": "admin",
            "lastName": "JackWang",
            "email": "admin@lyshark.com"
        },
        {
   
            "firstName": "lyshark",
            "lastName": "xusong",
            "email": "me@lyshark.com"
        }
    ],

  "get_my_list":
  {
   
        "get_uint": "[1,2,3,4,5,6,7,8,9,0]", 
        "get_string": "['admin','lyshark','root']"
    }
}

8.1 解析单个节点

代码中使用了 Boost C++ 库中的 property_tree 和 json_parser 来解析 JSON 文件。它的主要功能是读取指定路径下的 "c://config.json" 文件,然后获取其中的用户名和年龄信息(如果存在的话),并将它们输出到控制台。

#include <iostream>
#include <boost/property_tree/ptree.hpp>
#include <boost/property_tree/json_parser.hpp>

using namespace std;

int main(int argc, char* argv[])
{
   
  boost::property_tree::ptree ptr;
  boost::property_tree::read_json("c://config.json", ptr);

  cout << "是否存在: " << ptr.count("username") << endl;
  if (ptr.count("username") != 0)
  {
   
    std::string username = ptr.get<std::string>("username");
    std::cout << "用户名: " << username << std::endl;
  }

  if (ptr.count("age") != 0)
  {
   
    int age = ptr.get<int>("age");
    std::cout << "年龄: " << age << std::endl;
  }

  system("pause");
  return 0;
}

8.2 解析单个列表

代码中使用了 Boost C++ 库中的 property_tree 和 json_parser 来解析 JSON 文件。它的功能是读取指定路径下的 "c://config.json" 文件,并提取名为 "get_list" 的字段的值,并将其输出到控制台。

#include <iostream>
#include <vector>
#include <boost/property_tree/ptree.hpp>
#include <boost/property_tree/json_parser.hpp>

using namespace std;

void GetJson(std::string &filePath)
{
   
  boost::property_tree::ptree ptr;
  std::vector<std::string> item;

  boost::property_tree::read_json(filePath, ptr);

  // 先判断是否存在字段
  if (ptr.count("get_list") == 1)
  {
   
    boost::property_tree::ptree pChild = ptr.get_child("get_list");
    for (auto pos = pChild.begin(); pos != pChild.end(); ++pos)
    {
   
      // 迭代循环,将元素房补vector列表中
      std::string list = pos->second.get_value<string>();
      item.push_back(list);
    }
  }

  // 迭代输出vector中的数据
  for (auto x = item.begin(); x != item.end(); ++x)
  {
   
    cout << *x << endl;
  }
}

int main(int argc, char* argv[])
{
   
  GetJson(std::string("c://config.json"));
  system("pause");
  return 0;
}

8.3 解析嵌套列表

这段代码依然使用了 Boost C++ 库中的 property_tree 和 json_parser 来解析 JSON 文件。它的功能是读取指定路径下的 "c://config.json" 文件,并提取名为 "user_data" 的字段的第二列数据,并将其输出到控制台。

#include <iostream>
#include <vector>
#include <boost/property_tree/ptree.hpp>
#include <boost/property_tree/json_parser.hpp>

using namespace std;

void GetJson(std::string &filePath)
{
   
  boost::property_tree::ptree ptr;
  boost::property_tree::read_json(filePath, ptr);

  std::vector<std::string> item;

  for (auto& root_child : ptr.get_child("user_data"))
  {
   
    int count = 1;
    for (auto& x : root_child.second)
    {
   
      // count 用于指定需要那一列的记录
      if (count == 2)
      {
   
        std::string sub_data = x.second.get_value<std::string>();
        cout << "输出元素: " << sub_data << endl;
        item.push_back(sub_data);
      }
      count++;
    }
  }

  // 迭代输出vector中的数据
  for (auto x = item.begin(); x != item.end(); ++x)
  {
   
    cout << *x << endl;
  }
}

int main(int argc, char* argv[])
{
   
  GetJson(std::string("c://config.json"));
  system("pause");
  return 0;
}

8.4 解析多层字典

代码同样使用了 Boost C++ 库中的 property_tree 和 json_parser 来解析 JSON 文件。它的功能是读取指定路径下的 "c://config.json" 文件,并提取名为 "get_dict" 和 "user_dict" 的字段数据,并将其输出到控制台。

#include <iostream>
#include <vector>
#include <boost/property_tree/ptree.hpp>
#include <boost/property_tree/json_parser.hpp>

using namespace std;

void GetJson(std::string &filePath)
{
   
  boost::property_tree::ptree ptr;
  boost::property_tree::read_json(filePath, ptr);

  // 解析单一字典
  std::string username = ptr.get_child("get_dict").get<std::string>("username");
  cout << "姓名: " << username << endl;

  // 解析多层字典
  boost::property_tree::ptree root_ptr, item;
  root_ptr = ptr.get_child("user_dict");

  // 输出第二层
  for (boost::property_tree::ptree::iterator it = root_ptr.begin(); it != root_ptr.end(); ++it)
  {
   
    item = it->second;
    cout << "UID: " << item.get<int>("uid") << " 姓名: " << item.get<string>("uname") << endl;
  }
}

int main(int argc, char* argv[])
{
   
  GetJson(std::string("c://config.json"));
  system("pause");
  return 0;
}

第二种方式,通过多次迭代解析多层字典,并将字典中的特定value放入到vector容器内。

#include <iostream>
#include <string>
#include <boost/property_tree/ptree.hpp>
#include <boost/property_tree/json_parser.hpp>

using namespace std;
using namespace boost;
using namespace boost::property_tree;

int main(int argc, char *argv[])
{
   
  boost::property_tree::ptree ptr;
  boost::property_tree::read_json("C://config.json", ptr);

  // 判断是否存在get_root
  if (ptr.count("get_root") == 1)
  {
   
    std::vector<string> vecStr;
    std::string get_first_name;

    boost::property_tree::ptree p1, p2;

    // 读取到根节点
    p1 = ptr.get_child("get_root");

    // 循环枚举
    for (ptree::iterator it = p1.begin(); it != p1.end(); ++it)
    {
   
      // 获取到字典的value值
      p2 = it->second;
      get_first_name = p2.get<string>("firstName");

      // 将获取到的value转换为vector容器
      vecStr.push_back(get_first_name);
    }

    // 输出容器中的内容
    for (int x = 0; x < vecStr.size(); x++)
    {
   
      std::cout << vecStr[x] << std::endl;
    }
  }
  std::system("pause");
  return 0;
}

8.5 写出JSON文件

#include <iostream>
#include <boost/property_tree/ptree.hpp>
#include <boost/property_tree/json_parser.hpp>

using namespace std;

// 初始化字符串
bool InitJSON()
{
   
  string str = "{\"uuid\":1001,\"Student\":[{\"Name\":\"admin\"},{\"Name\":\"lyshark\"}]}";
  stringstream stream(str);
  boost::property_tree::ptree strTree;

  try{
   
    read_json(stream, strTree);
  }
  catch (boost::property_tree::ptree_error & e) {
   
    return false;
  }
  write_json("c://config.json", strTree);
  return true;
}

// 初始化列表
void InitArray()
{
   
  boost::property_tree::ptree ptr;
  boost::property_tree::ptree children;
  boost::property_tree::ptree child1, child2, child3;

  child1.put("", 1);
  child2.put("", 2);
  child3.put("", 3);

  children.push_back(std::make_pair("", child1));
  children.push_back(std::make_pair("", child2));
  children.push_back(std::make_pair("", child3));

  ptr.add_child("MyArray", children);
  write_json("c://Array.json", ptr);
}

// 初始化字典
void InitDict()
{
   
  boost::property_tree::ptree ptr;
  boost::property_tree::ptree children;
  boost::property_tree::ptree child1, child2, child3;

  child1.put("childkeyA", 1);
  child1.put("childkeyB", 2);

  child2.put("childkeyA", 3);
  child2.put("childkeyB", 4);

  child3.put("childkeyA", 5);
  child3.put("childkeyB", 6);

  children.push_back(std::make_pair("", child1));
  children.push_back(std::make_pair("", child2));
  children.push_back(std::make_pair("", child3));

  ptr.put("testkey", "testvalue");
  ptr.add_child("MyArray", children);

  write_json("c://MyDict.json", ptr);
}

int main(int argc, char* argv[])
{
   
  InitArray();
  InitDict();
  InitJSON();

  boost::property_tree::ptree ptr;
  boost::property_tree::read_json("c://config.json", ptr);

  // 修改uuid字段
  if (ptr.count("uuid") != 0)
  {
   
    ptr.put("uuid", 10002);
  }
  boost::property_tree::write_json("c://config.json", ptr);

  system("pause");
  return 0;
}

8.6 自定义结构解析

#include <iostream>
#include <string>
#include <vector>
#include <boost/assign.hpp>
#include <boost/lexical_cast.hpp>
#include <boost/algorithm/string.hpp>
#include <boost/property_tree/ptree.hpp>
#include <boost/property_tree/json_parser.hpp>

using namespace std;
using namespace boost;
using namespace boost::property_tree;

// 将整数转为int容器
std::vector<int> JsonIntToVector(std::string string_ptr)
{
   
  std::vector<std::string> vect;

  // 去掉里面的[]符号
  std::string item = boost::trim_copy_if(string_ptr, (boost::is_any_of("[") || boost::is_any_of("]")));
  boost::split(vect, item, boost::is_any_of(",,"), boost::token_compress_on);

  std::vector<int> ref;
  for (auto each : vect)
  {
   
    ref.push_back(boost::lexical_cast<int>(each));
  }
  return ref;
}

// 将字符串列表转为string容器
std::vector<std::string> JsonStringToVector(std::string string_ptr)
{
   
  std::vector<std::string> ref;
  std::vector<std::string> vect;

  std::string item = boost::trim_copy_if(string_ptr, (boost::is_any_of("[") || boost::is_any_of("]")));
  boost::split(vect, item, boost::is_any_of(",,"), boost::token_compress_on);

  for (auto each : vect)
  {
   
    // 去掉单引号
    std::string ea = boost::trim_copy_if(each, (boost::is_any_of("'") || boost::is_any_of("\"")));
    ref.push_back(ea);
  }
  return ref;
}

int main(int argc, char *argv[])
{
   
  boost::property_tree::ptree ptr;
  boost::property_tree::read_json("./config.json", ptr);

  // 输出特殊的整数
  std::string ustring = ptr.get_child("get_my_list").get<std::string>("get_uint");
  std::vector<int> ref_int = JsonIntToVector(ustring);
  for (int x = 0; x < ref_int.size(); x++)
  {
   
    std::cout << "输出整数: " << ref_int[x] << std::endl;
  }

  // 输出特殊的字符串
  std::string ustring1 = ptr.get_child("get_my_list").get<std::string>("get_string");
  std::vector<std::string> ref_string = JsonStringToVector(ustring1);
  for (int x = 0; x < ref_string.size(); x++)
  {
   
    std::cout << "输出字符串: " << ref_string[x] << std::endl;
  }

    std::system("pause");
    return 0;
}
相关文章
|
12天前
|
缓存 Kubernetes Docker
GitLab Runner 全面解析:Kubernetes 环境下的应用
GitLab Runner 是 GitLab CI/CD 的核心组件,负责执行由 `.gitlab-ci.yml` 定义的任务。它支持多种执行方式(如 Shell、Docker、Kubernetes),可在不同环境中运行作业。本文详细介绍了 GitLab Runner 的基本概念、功能特点及使用方法,重点探讨了流水线缓存(以 Python 项目为例)和构建镜像的应用,特别是在 Kubernetes 环境中的配置与优化。通过合理配置缓存和镜像构建,能够显著提升 CI/CD 流水线的效率和可靠性,助力开发团队实现持续集成与交付的目标。
|
8天前
|
JSON 前端开发 搜索推荐
关于商品详情 API 接口 JSON 格式返回数据解析的示例
本文介绍商品详情API接口返回的JSON数据解析。最外层为`product`对象,包含商品基本信息(如id、name、price)、分类信息(category)、图片(images)、属性(attributes)、用户评价(reviews)、库存(stock)和卖家信息(seller)。每个字段详细描述了商品的不同方面,帮助开发者准确提取和展示数据。具体结构和字段含义需结合实际业务需求和API文档理解。
|
1天前
|
JSON 缓存 API
解析电商商品详情API接口系列,json数据示例参考
电商商品详情API接口是电商平台的重要组成部分,提供了商品的详细信息,支持用户进行商品浏览和购买决策。通过合理的API设计和优化,可以提升系统性能和用户体验。希望本文的解析和示例能够为开发者提供参考,帮助构建高效、可靠的电商系统。
20 12
|
9天前
|
供应链 搜索推荐 API
深度解析1688 API对电商的影响与实战应用
在全球电子商务迅猛发展的背景下,1688作为知名的B2B电商平台,为中小企业提供商品批发、分销、供应链管理等一站式服务,并通过开放的API接口,为开发者和电商企业提供数据资源和功能支持。本文将深入解析1688 API的功能(如商品搜索、详情、订单管理等)、应用场景(如商品展示、搜索优化、交易管理和用户行为分析)、收益分析(如流量增长、销售提升、库存优化和成本降低)及实际案例,帮助电商从业者提升运营效率和商业收益。
82 17
|
1天前
|
JSON 小程序 UED
微信小程序 app.json 配置文件解析与应用
本文介绍了微信小程序中 `app.json` 配置文件的详细
28 12
|
12天前
|
C++ 芯片
【C++面向对象——类与对象】Computer类(头歌实践教学平台习题)【合集】
声明一个简单的Computer类,含有数据成员芯片(cpu)、内存(ram)、光驱(cdrom)等等,以及两个公有成员函数run、stop。只能在类的内部访问。这是一种数据隐藏的机制,用于保护类的数据不被外部随意修改。根据提示,在右侧编辑器补充代码,平台会对你编写的代码进行测试。成员可以在派生类(继承该类的子类)中访问。成员,在类的外部不能直接访问。可以在类的外部直接访问。为了完成本关任务,你需要掌握。
52 18
|
12天前
|
存储 编译器 数据安全/隐私保护
【C++面向对象——类与对象】CPU类(头歌实践教学平台习题)【合集】
声明一个CPU类,包含等级(rank)、频率(frequency)、电压(voltage)等属性,以及两个公有成员函数run、stop。根据提示,在右侧编辑器补充代码,平台会对你编写的代码进行测试。​ 相关知识 类的声明和使用。 类的声明和对象的声明。 构造函数和析构函数的执行。 一、类的声明和使用 1.类的声明基础 在C++中,类是创建对象的蓝图。类的声明定义了类的成员,包括数据成员(变量)和成员函数(方法)。一个简单的类声明示例如下: classMyClass{ public: int
38 13
|
12天前
|
编译器 数据安全/隐私保护 C++
【C++面向对象——继承与派生】派生类的应用(头歌实践教学平台习题)【合集】
本实验旨在学习类的继承关系、不同继承方式下的访问控制及利用虚基类解决二义性问题。主要内容包括: 1. **类的继承关系基础概念**:介绍继承的定义及声明派生类的语法。 2. **不同继承方式下对基类成员的访问控制**:详细说明`public`、`private`和`protected`继承方式对基类成员的访问权限影响。 3. **利用虚基类解决二义性问题**:解释多继承中可能出现的二义性及其解决方案——虚基类。 实验任务要求从`people`类派生出`student`、`teacher`、`graduate`和`TA`类,添加特定属性并测试这些类的功能。最终通过创建教师和助教实例,验证代码
37 5
|
12天前
|
存储 算法 搜索推荐
【C++面向对象——群体类和群体数据的组织】实现含排序功能的数组类(头歌实践教学平台习题)【合集】
1. **相关排序和查找算法的原理**:介绍直接插入排序、直接选择排序、冒泡排序和顺序查找的基本原理及其实现代码。 2. **C++ 类与成员函数的定义**:讲解如何定义`Array`类,包括类的声明和实现,以及成员函数的定义与调用。 3. **数组作为类的成员变量的处理**:探讨内存管理和正确访问数组元素的方法,确保在类中正确使用动态分配的数组。 4. **函数参数传递与返回值处理**:解释排序和查找函数的参数传递方式及返回值处理,确保函数功能正确实现。 通过掌握这些知识,可以顺利地将排序和查找算法封装到`Array`类中,并进行测试验证。编程要求是在右侧编辑器补充代码以实现三种排序算法
28 5
|
12天前
|
Serverless 编译器 C++
【C++面向对象——类的多态性与虚函数】计算图像面积(头歌实践教学平台习题)【合集】
本任务要求设计一个矩形类、圆形类和图形基类,计算并输出相应图形面积。相关知识点包括纯虚函数和抽象类的使用。 **目录:** - 任务描述 - 相关知识 - 纯虚函数 - 特点 - 使用场景 - 作用 - 注意事项 - 相关概念对比 - 抽象类的使用 - 定义与概念 - 使用场景 - 编程要求 - 测试说明 - 通关代码 - 测试结果 **任务概述:** 1. **图形基类(Shape)**:包含纯虚函数 `void PrintArea()`。 2. **矩形类(Rectangle)**:继承 Shape 类,重写 `Print
33 4

推荐镜像

更多