如何创建值可以是多种类型之一的 Rust HashMap?
Posted
技术标签:
【中文标题】如何创建值可以是多种类型之一的 Rust HashMap?【英文标题】:How do I create a Rust HashMap where the value can be one of multiple types? 【发布时间】:2017-01-01 23:06:26 【问题描述】:我想制作一个包含多种类型的 JSON 对象。这是结构:
"key1": "value",
"key2": ["val", "val", "val"]
"key3": "keyX": 12
如何创建一个接受所有这些类型的HashMap
?
我正在尝试这个:
let item = HashMap::new();
item.insert("key1", someString); //type is &str
item.insert("key2", someVecOfStrings); //type is Vec<String>
item.insert("key3", someOtherHashMap); //Type is HashMap<&str, u32>
let response = json::encode(&item).unwrap();
我知道哈希映射没有足够的类型信息,但我不确定如何使它工作。我尝试在item
上设置一个显式类型,即HashMap<&str, Encodable>
,但这只是另一个错误。这样做的正确方法是什么?
【问题讨论】:
【参考方案1】:您应该在HashMap
中使用枚举类型作为值。该枚举需要为每种可能的类型(布尔、数字、字符串、列表、映射...)提供一个变体,并为每个变体提供一个适当类型的关联值:
enum JsonValue<'a>
String(&'a str),
VecOfString(Vec<String>),
AnotherHashMap(HashMap<&'a str, u32>),
幸运的是,已经有了an implementation of a JSON value type,它是serde_json crate 的一部分,它建立在serde crate 之上。
如果您使用 serde_json crate,您的代码将如下所示:
extern crate serde_json;
use serde_json::Value, Map, Number;
fn main()
let mut inner_map = Map::new();
inner_map.insert("x".to_string(), Value::Number(Number::from(10u64)));
inner_map.insert("y".to_string(), Value::Number(Number::from(20u64)));
let mut map = Map::new();
map.insert("key1".to_string(), Value::String("test".to_string()));
map.insert(
"key2".to_string(),
Value::Array(vec![
Value::String("a".to_string()),
Value::String("b".to_string()),
]),
);
map.insert("key3".to_string(), Value::Object(inner_map));
println!("", serde_json::to_string(&map).unwrap());
// => "key1":"test","key2":["a","b"],"key3":"x":10,"y":20
【讨论】:
您能否提供一个示例如何执行我在问题中发布的示例?除了使用枚举之外没有其他方法吗?与其他语言相比,这似乎有点矫枉过正,但我不知道 Rust 是如何做到的,因为我才刚刚开始。 This crate 还可以让您轻松编写 JSON。 我添加了一个示例。为什么你认为这是矫枉过正?这是对 rust 枚举(标记的联合)的非常简单的使用。【参考方案2】:这是另一种可能更适合您的方法。 serde_json
crate 提供了一种从 JSON 文字构造 serde_json::Value
对象的方法。您的示例如下所示:
#[macro_use]
extern crate serde_json;
fn main()
let item = json!(
"key1": "value",
"key2": ["val", "val", "val"],
"key3": "keyX": 12
);
let response = serde_json::to_string(&item).unwrap();
【讨论】:
以上是关于如何创建值可以是多种类型之一的 Rust HashMap?的主要内容,如果未能解决你的问题,请参考以下文章