C++ 中的 JSON 序列化和反序列化:结构体与枚举类型的处理
在 C++ 编程中,处理 JSON 数据是一项常见任务,特别是在需要与其他系统或前端进行数据交换时。nlohmann::json
库是一个功能强大且易于使用的 JSON 库,它允许我们轻松地在 C++ 中进行 JSON 数据的序列化和反序列化。本文将详细介绍如何使用 nlohmann::json
库对结构体和枚举类型进行序列化和反序列化。
一、结构体的 JSON 序列化和反序列化
1. 序列化方法 to_json
要将结构体转换为 JSON 对象,我们需要定义一个 to_json
函数。这个函数接收一个 nlohmann::json
引用和一个结构体实例,并将结构体的字段填充到 JSON 对象中。
inline void to_json(nlohmann::json &j, const YourStruct &p)
{j = nlohmann::json{{"field1", p.field1},{"field2", p.field2},// 添加其他字段};
}
在这个例子中,YourStruct
是一个自定义的结构体,field1
和 field2
是它的字段。通过 to_json
函数,我们可以将 YourStruct
实例转换为 JSON 对象。
2. 反序列化方法 from_json
要从 JSON 对象中提取数据并填充到结构体中,我们需要定义一个 from_json
函数。这个函数同样接收一个 nlohmann::json
引用和一个结构体引用,并从 JSON 对象中提取数据并赋值给结构体的字段。
inline void from_json(const nlohmann::json &j, YourStruct &p)
{try {j.at("field1").get_to(p.field1);j.at("field2").get_to(p.field2);// 添加其他字段} catch (const nlohmann::json::exception& e) {// 处理解析错误,例如设置默认值或标记错误p.field1 = default_value1;p.field2 = default_value2;// 或者抛出异常// throw std::runtime_error("Failed to parse JSON: " + std::string(e.what()));}
}
在这个例子中,我们使用 try-catch
块来捕获可能的异常,例如 JSON 对象中缺少某个键。如果捕获到异常,我们可以选择设置默认值或抛出异常。
二、枚举类型的 JSON 序列化和反序列化
处理枚举类型的 JSON 序列化和反序列化时,我们可以使用 NLOHMANN_JSON_SERIALIZE_ENUM
宏来简化工作。
enum class YourEnum {Value1,Value2,// 添加其他枚举值
};NLOHMANN_JSON_SERIALIZE_ENUM(YourEnum,{ { YourEnum::Value1, "Value1" },{ YourEnum::Value2, "Value2" },// 添加其他枚举值})
在这个例子中,我们定义了一个枚举类型 YourEnum
,并使用 NLOHMANN_JSON_SERIALIZE_ENUM
宏来定义枚举值的字符串表示形式。这样,YourEnum::Value1
将被序列化为字符串 "Value1"
,反之亦然。
三、示例代码
假设我们有两个结构体 RobotMsg
和 RtdeRecipe
,以及两个枚举类型 RuntimeState
和 RobotModeType
。以下是完整的示例代码:
#include <nlohmann/json.hpp>
#include <vector>
#include <string>
#include <stdexcept>// 引入 JSON 库命名空间
using json = nlohmann::json;// 枚举类型定义及序列化
enum class RuntimeState {Running,Retracting,Pausing,Paused,Stopping,Stopped,Aborting
};NLOHMANN_JSON_SERIALIZE_ENUM(RuntimeState,{ { RuntimeState::Running, "Running" },{ RuntimeState::Retracting, "Retracting" },{ RuntimeState::Pausing, "Pausing" },{ RuntimeState::Paused, "Paused" },{ RuntimeState::Stopping, "Stopping" },{ RuntimeState::Stopped, "Stopped" },{ RuntimeState::Aborting, "Aborting" } })// 结构体定义及序列化/反序列化
struct RobotMsg {int64_t timestamp;int level;int code;std::string source;std::vector<std::string> args;
};inline void to_json(json &j, const RobotMsg &p)
{j = json{{"timestamp", p.timestamp},{"level", p.level},{"code", p.code},{"source", p.source},{"args", p.args}};
}inline void from_json(const json &j, RobotMsg &p)
{try {j.at("timestamp").get_to(p.timestamp);j.at("level").get_to(p.level);j.at("code").get_to(p.code);j.at("source").get_to(p.source);j.at("args").get_to(p.args);} catch (const json::exception& e) {// 解析无效p.code = -1;// 或者抛出异常// throw std::runtime_error("Failed to parse JSON: " + std::string(e.what()));}
}
相关文章:
C++ 中的 JSON 序列化和反序列化:结构体与枚举类型的处理
在 C 编程中,处理 JSON 数据是一项常见任务,特别是在需要与其他系统或前端进行数据交换时。nlohmann::json 库是一个功能强大且易于使用的 JSON 库,它允许我们轻松地在 C 中进行 JSON 数据的序列化和反序列化。本文将详细介绍如何使用 nlohma…...
MySQL 批量删除海量数据的几种方法
目录 一、问题分析 二、批量删除海量数据的几种方法 方法 1:使用 LIMIT 分批删除 方法 2:通过主键范围分批删除 方法 3:通过自定义批量删除存储过程 方法 4:创建临时表替换旧表 三、性能优化建议 总结 在数据库的日常维护…...

【docker入门】docker的安装
目录 Centos 7 添加docker 官方仓库到yum源 将 Docker 的官方镜像源替换为国内可以的 Docker 镜像源 安装docker 配置docker加速源 Ubuntu 创建 gpg key 目录 下载 gpg key 添加国内可用镜像源到 系统的 APT 仓库中 安装docker 配置加速源 Centos 7 添加docker 官方仓…...
单例模式五种写法
饿汉式(线程安全) public class Singleton {// 直接创建实例,在类加载时就完成实例化private static final Singleton instance new Singleton();// 私有构造函数private Singleton() {}// 提供公共的静态方法获取实例public static Single…...

解析静态链接
文章目录 静态链接空间与地址分配相似段合并虚拟地址分配符号地址确定 符号解析与重定位链接器优化重复代码消除函数链接级别 静态库静态链接优缺点 静态链接 一组目标文件经过链接器链接后形成的文件即可执行文件,如果没有动态库的加入,那么这个可执行…...

前端基础-html-注册界面
(200粉啦,感谢大家的关注~ 一起加油吧~) 浅浅分享下作业,大佬轻喷~ 网页最终效果: 详细代码: <!DOCTYPE html> <html lang"en"><head><meta charset"UTF-8"…...
量子电路的实现 基于ibm的qiskit
量子计算的物理实现 量子计算的实现有几种方式,最常用的就是超导量子计算机,它的量子处理器是用超导传输量子比特构建的,它是由一个约瑟夫森结和一个并联的电容器组成的电路。约瑟夫森结是一种非线性电感,由两层重叠的超导…...

关于谷歌浏览器debug模式不进断点问题解决方案
第一步.浏览器F12弹出调试者模式 第二步.点击设置齿轮,找到Ignore List,将node_model取消勾选,关闭浏览器,重新打开就进断点了...
制造行业实践|悠进电装基于超融合完成信息化改造, 保障业务系统 7/24 长跑
当一辆汽车在路上奔驰时,确保车内各种电气信号正常传递和电力供给的关键是什么?正是那不起眼却功不可没的汽车线束。这些精密编织的电线网络,犹如汽车的“神经网络”和“动脉血管”,在传递电气信号、数据的同时,源源不…...

如何学习C++游戏开发
学习C游戏开发是一个涉及多个领域的复杂过程,包括编程、游戏设计、图形学等。 1. **学习C基础**: - 掌握C的基本语法和面向对象编程。 - 学习C标准库,特别是STL(标准模板库)。 2. **理解游戏开发概念**…...

计算网络信号
题目描述: 网络信号经过传递会逐层衰减,且遇到阻隔物无法直接穿透,在此情况下需要计算某个位置的网络信号值。注意:网络信号可以绕过阻隔物 array[m][n]的二维数组代表网格地图, array[i][j]0代表i行j列是空旷位置&…...
【Vue 全家桶】6、vue-router 路由(更新中)
目录 相关理解基本路由嵌套路由路由传参编程式路由导航 相关理解 基本路由 嵌套路由 路由传参 编程式路由导航...

解决程序因缺少xinput1_3.dll无法运行的有效方法,有效修复丢失xinput1_3.dll
如果你的电脑在运行某些应用程序或游戏时提示“xinput1_3.dll丢失”或“找不到xinput1_3.dll”的错误消息,那么很可能是因为你的系统中缺少这个重要的DLL文件而导致的问题。那么电脑出现xinput1_3.dll丢失的问题时有哪些方法进行修复呢? 如何确定电脑是否…...
uni-popup 弹出框
:maskClick"false" 是点击空白遮罩处不关闭弹窗 <uni-popup ref"popup" type"center" :maskClick"false"> <div style"width: 80vw;padding: 0.5em;box-sizing: border-box; background-color: #fff; border-…...
Android笔记:Android中Fragment改变主题
在Android中,Fragment使用主题可以通过以下几种方法实现: 1 在onCreateView方法中设置主题: 在onCreateView方法中,可以通过创建一个ContextThemeWrapper来改变Fragment的主题。例如: @Override public View onCreateView(LayoutInflater inflater, ViewGroup co…...
GEE 训练——利用sentinel-2数据计算两栖NDVI前后差异
目录 简介 函数 expression(expression, map) Arguments: Returns: Image 代码 结果 简介 利用sentinel-2数据计算两栖NDVI前后差异 COPERNICUS/S2是欧洲空间局(ESA)的地球观测计划,旨在通过卫星遥感技术提供全球的高分辨率地球观测数据。S2是COPERNICUS地球观测计…...

看电动缸是如何提高农机的自动化水平
电动缸作为一种将电动机的旋转运动转变为推杆的直线往复运动的电力驱动装置,在提升农机自动化水平方面发挥了重要作用。以下详细分析电动缸如何提高农机的自动化水平: 一、电动缸的工作原理与优势 电动缸的工作原理是以电力作为直接动力源,采…...
C++ 并发专题 - 条件变量的使用
一:概述: 在 C 中,条件变量(std::condition_variable)是一种用于线程间同步的机制,主要用于在多线程环境中让一个线程等待某个条件满足后再继续执行。条件变量通常配合互斥锁(std::mutex&#…...
《Essential C++》学习笔记
《Essential C》这本书,是适合从C选手快速过度到C选手的 一本书,下面是个人记录 第一章:基础语法 第一章主要就是C语言基础,这里类似于表达式 数组 条件语句 循环语句,就不多概述了。 :::info vector:可动…...
揭秘!微服务架构下,Apollo 配置中心凭啥扮演关键角色?
在当今的微服务架构蓬勃发展的时代,配置中心扮演着极为关键的角色,其重要性不言而喻。今天,我们就以 Apollo 为例,聊聊配置中心在微服务架构中的重要意义。 一、微服务架构下的配置管理挑战 随着微服务架构的广泛应用࿰…...

微软PowerBI考试 PL300-选择 Power BI 模型框架【附练习数据】
微软PowerBI考试 PL300-选择 Power BI 模型框架 20 多年来,Microsoft 持续对企业商业智能 (BI) 进行大量投资。 Azure Analysis Services (AAS) 和 SQL Server Analysis Services (SSAS) 基于无数企业使用的成熟的 BI 数据建模技术。 同样的技术也是 Power BI 数据…...

UE5 学习系列(三)创建和移动物体
这篇博客是该系列的第三篇,是在之前两篇博客的基础上展开,主要介绍如何在操作界面中创建和拖动物体,这篇博客跟随的视频链接如下: B 站视频:s03-创建和移动物体 如果你不打算开之前的博客并且对UE5 比较熟的话按照以…...

12.找到字符串中所有字母异位词
🧠 题目解析 题目描述: 给定两个字符串 s 和 p,找出 s 中所有 p 的字母异位词的起始索引。 返回的答案以数组形式表示。 字母异位词定义: 若两个字符串包含的字符种类和出现次数完全相同,顺序无所谓,则互为…...
Caliper 配置文件解析:config.yaml
Caliper 是一个区块链性能基准测试工具,用于评估不同区块链平台的性能。下面我将详细解释你提供的 fisco-bcos.json 文件结构,并说明它与 config.yaml 文件的关系。 fisco-bcos.json 文件解析 这个文件是针对 FISCO-BCOS 区块链网络的 Caliper 配置文件,主要包含以下几个部…...

全志A40i android7.1 调试信息打印串口由uart0改为uart3
一,概述 1. 目的 将调试信息打印串口由uart0改为uart3。 2. 版本信息 Uboot版本:2014.07; Kernel版本:Linux-3.10; 二,Uboot 1. sys_config.fex改动 使能uart3(TX:PH00 RX:PH01),并让boo…...
Angular微前端架构:Module Federation + ngx-build-plus (Webpack)
以下是一个完整的 Angular 微前端示例,其中使用的是 Module Federation 和 npx-build-plus 实现了主应用(Shell)与子应用(Remote)的集成。 🛠️ 项目结构 angular-mf/ ├── shell-app/ # 主应用&…...
Java数值运算常见陷阱与规避方法
整数除法中的舍入问题 问题现象 当开发者预期进行浮点除法却误用整数除法时,会出现小数部分被截断的情况。典型错误模式如下: void process(int value) {double half = value / 2; // 整数除法导致截断// 使用half变量 }此时...

GitFlow 工作模式(详解)
今天再学项目的过程中遇到使用gitflow模式管理代码,因此进行学习并且发布关于gitflow的一些思考 Git与GitFlow模式 我们在写代码的时候通常会进行网上保存,无论是github还是gittee,都是一种基于git去保存代码的形式,这样保存代码…...

【Linux】Linux 系统默认的目录及作用说明
博主介绍:✌全网粉丝23W,CSDN博客专家、Java领域优质创作者,掘金/华为云/阿里云/InfoQ等平台优质作者、专注于Java技术领域✌ 技术范围:SpringBoot、SpringCloud、Vue、SSM、HTML、Nodejs、Python、MySQL、PostgreSQL、大数据、物…...
Git常用命令完全指南:从入门到精通
Git常用命令完全指南:从入门到精通 一、基础配置命令 1. 用户信息配置 # 设置全局用户名 git config --global user.name "你的名字"# 设置全局邮箱 git config --global user.email "你的邮箱example.com"# 查看所有配置 git config --list…...