问题描述
我想从Test
对象本身的数据中反序列化Test::team_size
属性:
I want to have the Test::team_size
attribute be deserialized from the data of Test
object itself:
#[derive(Debug, Serialize, Deserialize)]
struct TeamSize {
pub min: i64,
pub max: i64,
}
#[derive(Debug, Serialize, Deserialize)]
struct Test {
pub i: i64,
pub team_size: TeamSize,
}
fn main() {
let t: Test = serde_json::from_str(r#"{"i": -2, "min": 2, "max": 5}"#).unwrap();
assert_eq!(t.i, -2);
assert_eq!(t.team_size.min, 2);
assert_eq!(t.team_size.max, 5);
}
此代码无法编译,我不知道如何使Serde满足我的要求.在此示例中,是否有办法从作为子字段的原始结构的JSON反序列化team_size
?
This code does not compile and I don't know how to make Serde do what I want. Is there a way to deserialize team_size
in this example from the JSON of the original structure where it is a subfield?
似乎我想要类似的东西 #[serde(untagged)]
但是对于一个结构和一个字段,而不是整个结构.
It seems that I want something like #[serde(untagged)]
but for a struct and for a field and not the whole struct.
推荐答案
从Serde 1.0.34开始,您现在可以使用 #[serde(flatten)]
:
As of Serde 1.0.34, you can now use #[serde(flatten)]
:
#[derive(Debug, Serialize, Deserialize)]
struct Test {
pub i: i64,
#[serde(flatten)]
pub team_size: TeamSize,
}
在此之前,最简单的解决方法是将反序列化为私有帮助程序类型并根据需要对其进行重组:
Before this, the easiest workaround would be to deserialize into a private helper type and restructure it as needed:
#[macro_use]
extern crate serde_derive;
extern crate serde;
extern crate serde_json;
use serde::{Serialize, Serializer, Deserialize, Deserializer};
#[derive(Debug)]
pub struct TeamSize {
pub min: i64,
pub max: i64,
}
#[derive(Debug)]
pub struct Test {
pub i: i64,
pub team_size: TeamSize,
}
// Private helper
#[derive(Serialize, Deserialize)]
struct Helper {
pub i: i64,
pub min: i64,
pub max: i64,
}
impl Serialize for Test {
fn serialize<S>(&self, serializer: S) -> Result<S::Ok, S::Error>
where S: Serializer
{
let helper = Helper {
i: self.i,
min: self.team_size.min,
max: self.team_size.max,
};
helper.serialize(serializer)
}
}
impl<'de> Deserialize<'de> for Test {
fn deserialize<D>(deserializer: D) -> Result<Self, D::Error>
where D: Deserializer<'de>
{
let helper = Helper::deserialize(deserializer)?;
Ok(Test {
i: helper.i,
team_size: TeamSize {
min: helper.min,
max: helper.max,
},
})
}
}
fn main() {
let j = r#" { "i": -2, "min": 2, "max": 5 } "#;
let de: Test = serde_json::from_str(j).unwrap();
println!("{:#?}", de);
let ser = serde_json::to_string_pretty(&de).unwrap();
println!("{}", ser);
}
这篇关于如何使用Serde从原始结构的JSON反序列化结构的子字段?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持!