![](/img/trans.png)
[英]Serde Stream Deserializer for a type other than serde_json::Value
[英]error: the type of this value must be known in this context (Rust) / serde_json Value
我正在使用serde_json反序列化json文档。 我有一个函数,给定一个字符串(这是json文档),将返回一个serde_json值(这是一个代表json类型的枚举),返回一个Option。 该值将根据需要传递给其他函数。
但是,我意识到传递一个值并不是我想要的,因为这样做,键不可用。
为了说明我的观点,如果我有一个像这样的json文档:
{
"root" : {
"regex" : null,
"prefixes" : [ "a_", "b_" ]
}
}
“ root”是json对象,“ regex”是json Null,“ prefixes”是json数组。
现在,json类型的Value是一个枚举类型,该标识符带有表示json类型的标识符,例如上面给出的示例的Object,Null,Array。
serde_json板条箱使用std :: collections :: BTreeMap表示json文档中的节点,其中String类型表示json键(在上面,它们是“ root”,“ regex”和“ prefixes”。因此,传递仅仅引用Values只是部分有用,我应该改为传递BTreeMap,以便我也可以访问键。
因此,这是我尝试重新编写的以下函数:
fn get_json_content(content_s : &str) -> Option<Value> {
// instead of returning a value, we need to return a BTreeMap, so we can get the
// key and the value.
println!("===>>> json_content obtained: {}", content_s);
match serde_json::from_str(content_s) { // -> Result<Value>
Ok(some_value) => Some(some_value),
Err(_) => None
}
}
因此,我开始重新编写该函数,但遇到“在此情况下必须知道此值的类型”错误:
fn get_json_content_as_btreemap<'a>(content_s : &str) -> Option<&'a BTreeMap<String, Value>> {
match serde_json::from_str(content_s) { // -> Result<Value>
Ok(some) => {
// I expect the type of key_value_pair to be BTreeMap<String, Value>>
// (but I may be wrong!)
let key_value_pair = some.as_object().unwrap(); // Error here
},
Err(_) => None
}
}
我在stackoverflow上发现了其他类似问题: 在这种情况下必须知道该值的类型
并将其用作帮助程序,我尝试如下插入类型:
let key_value_pair = some.as_object::<BTreeMap<_, _>>().unwrap();
这不能解决问题。 另外,尝试了其他类似的变体也无济于事。 那我该如何解决呢?
编辑:
我在此应用程序中具有另一个功能,如下所示:
fn get_root_value<'a>(json_documemt : &'a Value) -> Result<&'a Value, JsonErrorCode> {
if json_documemt.is_object() {
for (k, v) in json_documemt.as_object().unwrap().iter() {
if k == "root" {
println!("found root: {}", k);
return Ok(v)
}
}
return Err(JsonErrorCode::Custom("Failed to find root node".to_string()))
}
Err(JsonErrorCode::Custom("Not an object".to_string()))
}
...,这很好。 在这里,您可以看到我可以调用as_object(),然后以元组对的形式获取键和值。 我不明白为什么as_object在一种情况下起作用,而在另一种情况下却不起作用。 我想拉出BTreeMap并将其作为借来的项目传递出去。
您可以更改初始函数的返回类型,如果可以, serde_json
将反序列化为相应的对象:
fn get_json_content(content_s : &str) -> Option<BTreeMap<String, Value>> {
// instead of returning a value, we need to return a BTreeMap, so we can get the
// key and the value.
println!("===>>> json_content obtained: {}", content_s);
match serde_json::from_str(content_s) { // -> Result<Value>
Ok(some_value) => Some(some_value),
Err(_) => None
}
// Note: this match statement can be rewritten as
// serde_json::from_str(content_s).ok()
}
第二个示例将不起作用,因为您正在实例化函数内的Value
对象,然后尝试返回对刚实例化的对象的引用。 这将行不通,因为该对象将在函数末尾超出范围,然后引用将无效。
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.