我如何懒惰地从Rust中的文件/流中读取多个JSON值?
Posted
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了我如何懒惰地从Rust中的文件/流中读取多个JSON值?相关的知识,希望对你有一定的参考价值。
我想从Rust中的文件/阅读器中读取多个JSON对象,一次一个。不幸的是serde_json::from_reader(...)
只读到文件结尾;似乎没有任何方法可以使用它来读取单个对象或懒惰地迭代对象。
有没有办法做到这一点?使用serde_json
将是理想的,但如果有一个不同的库我会愿意使用它。
目前我将每个对象放在一个单独的行上并单独解析它们,但我真的不想这样做。
示例使用
main.rs
use serde_json;
fn main() -> Result<(), Box<dyn std::error::Error>> {
let stdin = std::io::stdin();
let stdin = stdin.lock();
for item in serde_json::iter_from_reader(stdin) {
println!("Got {:?}", item);
}
Ok(())
}
in.txt
{"foo": ["bar", "baz"]} 1 2 [] 4 5 6
example session
Got Object({"foo": Array([String("bar"), String("baz")])})
Got Number(1)
Got Number(2)
Got Array([])
Got Number(4)
Got Number(5)
Got Number(6)
答案
当I wanted to do it in Python,这是一个痛苦,但幸运的是在Rust这是事实上标准的serde_json
板条箱的直接支持功能!它不作为单个便利函数公开,但我们只需要从我们的文件/阅读器创建a serde_json::Deserializer
读取,然后使用其.into_iter()
方法获得a StreamDeserializer
iterator,产生包含Result
JSON值的serde_json::Value
s。
use serde_json;
fn main() -> Result<(), Box<dyn std::error::Error>> {
let stdin = std::io::stdin();
let stdin = stdin.lock();
let deserializer = serde_json::Deserializer::from_reader(stdin);
let iterator = deserializer.into_iter::<serde_json::Value>();
for item in iterator {
println!("Got {:?}", item?);
}
Ok(())
}
有一点需要注意:如果遇到语法错误,迭代器将开始产生无限的错误结果序列,永远不会继续前进。您需要确保处理循环内部的错误,否则循环将永远不会结束。在上面的代码片段中,我们通过使用?
问号运算符来打破循环并从我们的函数返回第一个serde_json::Result::Err
。
以上是关于我如何懒惰地从Rust中的文件/流中读取多个JSON值?的主要内容,如果未能解决你的问题,请参考以下文章