Serde 是一個(gè)用于序列化和反序列化 Rust 數(shù)據(jù)結(jié)構(gòu)的庫。它支持 JSON、BSON、YAML 等多種格式,并且可以自定義序列化和反序列化方式。Serde 的特點(diǎn)是代碼簡(jiǎn)潔、易于使用、性能高效。它是 Rust 生態(tài)中最受歡迎的序列化庫之一。
基礎(chǔ)用法
安裝
在 Rust 項(xiàng)目中使用 Serde,需要在Cargo.toml
文件中添加如下依賴:
[dependencies]
serde = { version = "1.0", features = ["derive"] }
其中features = ["derive"]
表示使用 Serde 的派生宏,可以自動(dòng)生成序列化和反序列化代碼。
序列化
使用 Serde 進(jìn)行序列化,需要先將數(shù)據(jù)結(jié)構(gòu)實(shí)現(xiàn)serde::Serialize
trait。例如,我們定義一個(gè)Animal
結(jié)構(gòu)體,包含名稱和年齡兩個(gè)字段:
#[derive(Serialize)]
struct Animal {
name: String,
age: u32,
}
然后,我們可以使用serde_json
庫將Animal
結(jié)構(gòu)體序列化為 JSON 字符串:
use serde_json;
let animal = Animal {
name: "Tom".to_owned(),
age: 3,
};
let json = serde_json::to_string(&animal).unwrap();
println!("{}", json); // {"name":"Tom","age":3}
反序列化
使用 Serde 進(jìn)行反序列化,需要先將數(shù)據(jù)結(jié)構(gòu)實(shí)現(xiàn)serde::Deserialize
trait。例如,我們定義一個(gè)Animal
結(jié)構(gòu)體,包含名稱和年齡兩個(gè)字段:
#[derive(Deserialize)]
struct Animal {
name: String,
age: u32,
}
然后,我們可以使用serde_json
庫將 JSON 字符串反序列化為Animal
結(jié)構(gòu)體:
use serde_json;
let json = r#"{"name":"Tom","age":3}"#;
let animal: Animal = serde_json::from_str(json).unwrap();
println!("{:?}", animal); // Animal { name: "Tom", age: 3 }
進(jìn)階用法
自定義序列化和反序列化
如果默認(rèn)的序列化和反序列化方式無法滿足需求,可以自定義序列化和反序列化方式。例如,我們定義一個(gè)Animal
結(jié)構(gòu)體,包含名稱和年齡兩個(gè)字段,但是希望在序列化時(shí),將名稱轉(zhuǎn)換為大寫字母,反序列化時(shí),將名稱轉(zhuǎn)換為小寫字母:
use serde::{Serialize, Deserialize, Serializer, Deserializer};
#[derive(Serialize, Deserialize)]
struct Animal {
#[serde(serialize_with = "serialize_name", deserialize_with = "deserialize_name")]
name: String,
age: u32,
}
fn serialize_name< S >(name: &String, serializer: S) - > Result< S::Ok, S::Error >
where
S: Serializer,
{
serializer.serialize_str(&name.to_uppercase())
}
fn deserialize_name< 'de, D >(deserializer: D) - > Result< String, D::Error >
where
D: Deserializer< 'de >,
{
let name = String::deserialize(deserializer)?;
Ok(name.to_lowercase())
}
在Animal
結(jié)構(gòu)體中,我們使用#[serde(serialize_with = "serialize_name", deserialize_with = "deserialize_name")]
指定了自定義的序列化和反序列化方法。serialize_name
函數(shù)將名稱轉(zhuǎn)換為大寫字母,deserialize_name
函數(shù)將名稱轉(zhuǎn)換為小寫字母。
序列化和反序列化枚舉
Serde 支持序列化和反序列化枚舉類型。例如,我們定義一個(gè)Animal
枚舉,包含狗和貓兩種類型:
use serde::{Serialize, Deserialize};
#[derive(Serialize, Deserialize)]
enum Animal {
Dog { name: String, age: u32 },
Cat { name: String, age: u32 },
}
在序列化和反序列化枚舉類型時(shí),需要使用#[serde(tag = "type")]
指定枚舉類型的標(biāo)簽,例如:
use serde_json;
let dog = Animal::Dog { name: "Tom".to_owned(), age: 3 };
let json = serde_json::to_string(&dog).unwrap();
println!("{}", json); // {"type":"Dog","name":"Tom","age":3}
let json = r#"{"type":"Dog","name":"Tom","age":3}"#;
let dog: Animal = serde_json::from_str(json).unwrap();
println!("{:?}", dog); // Dog { name: "Tom", age: 3 }
序列化和反序列化結(jié)構(gòu)體中的 Option
Serde 支持序列化和反序列化結(jié)構(gòu)體中的Option
類型。例如,我們定義一個(gè)Animal
結(jié)構(gòu)體,包含名稱和年齡兩個(gè)字段,其中名稱可以為空:
use serde::{Serialize, Deserialize};
#[derive(Serialize, Deserialize)]
struct Animal {
name: Option< String >,
age: u32,
}
在序列化和反序列化結(jié)構(gòu)體中的Option
類型時(shí),需要使用#[serde(skip_serializing_if = "Option::is_none")]
指定當(dāng)Option
值為None
時(shí),不進(jìn)行序列化。例如:
use serde_json;
let animal = Animal { name: Some("Tom".to_owned()), age: 3 };
let json = serde_json::to_string(&animal).unwrap();
println!("{}", json); // {"name":"Tom","age":3}
let animal = Animal { name: None, age: 3 };
let json = serde_json::to_string(&animal).unwrap();
println!("{}", json); // {"age":3}
let json = r#"{"age":3}"#;
let animal: Animal = serde_json::from_str(json).unwrap();
println!("{:?}", animal); // Animal { name: None, age: 3 }
序列化和反序列化結(jié)構(gòu)體中的 Vec
Serde 支持序列化和反序列化結(jié)構(gòu)體中的Vec
類型。例如,我們定義一個(gè)Zoo
結(jié)構(gòu)體,包含多個(gè)Animal
:
use serde::{Serialize, Deserialize};
#[derive(Serialize, Deserialize)]
struct Zoo {
animals: Vec< Animal >,
}
在序列化和反序列化結(jié)構(gòu)體中的Vec
類型時(shí),Serde 會(huì)自動(dòng)處理序列化和反序列化。例如:
use serde_json;
let zoo = Zoo { animals: vec![
Animal { name: "Tom".to_owned(), age: 3 },
Animal { name: "Jerry".to_owned(), age: 2 },
] };
let json = serde_json::to_string(&zoo).unwrap();
println!("{}", json); // {"animals":[{"name":"Tom","age":3},{"name":"Jerry","age":2}]}
let json = r#"{"animals":[{"name":"Tom","age":3},{"name":"Jerry","age":2}]}"#;
let zoo: Zoo = serde_json::from_str(json).unwrap();
println!("{:?}", zoo); // Zoo { animals: [Animal { name: "Tom", age: 3 }, Animal { name: "Jerry", age: 2 }] }
序列化和反序列化結(jié)構(gòu)體中的 HashMap
Serde 支持序列化和反序列化結(jié)構(gòu)體中的HashMap
類型。例如,我們定義一個(gè)Zoo
結(jié)構(gòu)體,包含多個(gè)Animal
,使用HashMap
存儲(chǔ):
use std::collections::HashMap;
use serde::{Serialize, Deserialize};
#[derive(Serialize, Deserialize)]
struct Zoo {
animals: HashMap< String, Animal >,
}
在序列化和反序列化結(jié)構(gòu)體中的HashMap
類型時(shí),Serde 會(huì)自動(dòng)處理序列化和反序列化。例如:
use serde_json;
let mut animals = HashMap::new();
animals.insert("Tom".to_owned(), Animal { name: "Tom".to_owned(), age: 3 });
animals.insert("Jerry".to_owned(), Animal { name: "Jerry".to_owned(), age: 2 });
let zoo = Zoo { animals };
let json = serde_json::to_string(&zoo).unwrap();
println!("{}", json); // {"animals":{"Jerry":{"name":"Jerry","age":2},"Tom":{"name":"Tom","age":3}}}
let json = r#"{"animals":{"Jerry":{"name":"Jerry","age":2},"Tom":{"name":"Tom","age":3}}}"#;
let zoo: Zoo = serde_json::from_str(json).unwrap();
println!("{:?}", zoo); // Zoo { animals: {"Tom": Animal { name: "Tom", age: 3 }, "Jerry": Animal { name: "Jerry", age: 2 }} }
總結(jié)
本教程介紹了如何使用 Serde 進(jìn)行序列化和反序列化,并且介紹了如何自定義序列化和反序列化邏輯。使用 Serde 可以輕松地將 Rust 數(shù)據(jù)結(jié)構(gòu)轉(zhuǎn)換為任何格式,并且可以通過自定義序列化和反序列化邏輯實(shí)現(xiàn)更高級(jí)的功能。
-
函數(shù)
+關(guān)注
關(guān)注
3文章
4346瀏覽量
62968 -
代碼
+關(guān)注
關(guān)注
30文章
4825瀏覽量
69041 -
數(shù)據(jù)結(jié)構(gòu)
+關(guān)注
關(guān)注
3文章
573瀏覽量
40230
發(fā)布評(píng)論請(qǐng)先 登錄
相關(guān)推薦
評(píng)論