enums - 有没有办法在 Rust 中“扁平化”枚举以进行(反)序列化?
问题描述
我有一个由其他枚举组成的枚举,类似于以下内容(serde
为简洁起见,省略了派生和注释):
enum Main {
A(SubA),
B(SubB),
}
enum SubA { X1, X2, X3 }
enum SubB { Y1, Y2, Y3 }
我希望能够用来serde
反序列化诸如“X1”或“Y3”之类的字符串,并分别自动取回 aMain::A(SubA::X1)
或Main::B(SubB::Y3)
。
我知道它serde
支持#[serde(transparent)]
newtype-style 结构的属性,这会做我喜欢的事情。但是,它似乎只适用于结构或枚举级别,而不是枚举变量级别。有没有一种方法可以自动获得我正在寻找的行为?我可以确保任何包含的子枚举中的任何变体名称都不会重叠。
除了希望保持 Rust 2018 稳定之外,我对我的项目没有其他限制,并且我愿意接受任何有用的 crate 建议。
解决方案
serde(untagged)
如果您放置外部枚举并且内部枚举没有什么特别之处,它几乎可以开箱即用:
use serde_derive::{Deserialize, Serialize};
#[derive(Debug, Deserialize, Serialize, PartialEq)]
#[serde(untagged)]
enum Main {
A(SubA),
B(SubB),
}
#[derive(Debug, Deserialize, Serialize, PartialEq)]
enum SubA { X1, X2, X3 }
#[derive(Debug, Deserialize, Serialize, PartialEq)]
enum SubB { Y1, Y2, Y3 }
fn main() {
let x1 = Main::A(SubA::X1);
let y2 = Main::B(SubB::Y2);
assert_eq!(serde_json::to_string(&x1).unwrap(), "\"X1\"");
assert_eq!(serde_json::to_string(&y2).unwrap(), "\"Y2\"");
assert_eq!(serde_json::de::from_str::<Main>("\"X1\"").unwrap(), x1);
assert_eq!(serde_json::de::from_str::<Main>("\"Y2\"").unwrap(), y2);
}
推荐阅读
- vb.net-2010 - 我怎样才能在我的图片框中看到图像?
- c# - ASP.NET Core 2.0 Identity,2 个控制器分别重定向到不同的登录页面
- html - 根据背景设置表格最后一个元素的边框
- powerbi - 创建一个新列并以数字值显示
- ios - android 库的 Swift 替代品
- reactjs - React Unexpected token < - babel loader
- r - WGCNA - modulePreservation() 中的错误:不允许重复的 row.names
- javascript - target="_blank" 在某些移动设备上不起作用
- sql-server - 通过预过滤结果加速 SQL 视图
- javascript - Vuex:如何定义一个状态变量,其值基于另一个状态变量的值?