Cut*_*ufo 3 json struct rust deserialization serde
我正在尝试将以下 JSON 片段反序列化为Vecof struct Shape:
use serde::{Deserialize, Serialize};
use serde_json::{Result, Value};
#[derive(Debug, Serialize, Deserialize)]
struct Shape { // this struct is not working, for display purpose only
shape_type: String,
d0: f64,
d1: f64,
d2: f64, //optional, like the case of "dot"
d3: f64, //optional, like the case of "circle"
}
let json = r#"
{[
["line", 1.0, 1.0, 2.0, 2.0],
["circle", 3.0, 3.0, 1.0],
["dot", 4.0, 4.0]
]}"#;
let data: Vec<Shape> = match serde_json::from_str(json)?;
Run Code Online (Sandbox Code Playgroud)
显然,每种类型都Shape需要String不同数量的f64来描述它。我应该如何定义 struct 来Shape反序列化上面的 JSON 数据?
假设您可以控制 JSON 格式,我强烈建议将Shape类型制作为可以表示多种形状的类型enum,并使用 serde 的派生宏自动实现Serialize和Deserializefor Shape。例子:
use serde::{Deserialize, Serialize};
#[derive(Debug, Serialize, Deserialize)]
struct Point {
x: f64,
y: f64,
}
#[derive(Debug, Serialize, Deserialize)]
#[serde(tag = "type")]
enum Shape {
Dot { position: Point },
Line { start: Point, end: Point },
Circle { center: Point, radius: f64 },
}
fn main() {
let shapes = vec![
Shape::Dot {
position: Point { x: 3.0, y: 4.0 },
},
Shape::Line {
start: Point { x: -2.0, y: 1.0 },
end: Point { x: 5.0, y: -3.0 },
},
Shape::Circle {
center: Point { x: 0.0, y: 0.0 },
radius: 7.0,
},
];
let serialized = serde_json::to_string(&shapes).unwrap();
println!("serialized = {}", serialized);
let deserialized: Vec<Shape> = serde_json::from_str(&serialized).unwrap();
println!("deserialized = {:?}", deserialized);
}
Run Code Online (Sandbox Code Playgroud)
如果您绝对无法更改 JSON 格式,那么 serde 无法帮助您。将形状序列化为字符串和浮点数的异构数组是一个非常奇怪的选择。您必须自己手动解析它(或者至少使用一些解析器箱来帮助您),然后手动实现反序列化器特征,将其转换为Shape.
| 归档时间: |
|
| 查看次数: |
10520 次 |
| 最近记录: |