[英]Stream online json information asynchronously
我正在尝试制作一个程序,该程序使用数据来寻找大型 3D 数学网络的解决方案。 在 JSON 格式中,有一个节点数组和有关它们在 3D 空间中的位置以及它们具有什么属性等的信息。您可以请求两种格式:
标准 JSON 数组: https://www.example.com/nodes.json
: https://www.example.com/nodes.json
[{"ID": 1, "Type": "Node", "x": 0, "y": 0, "z": 0}, {"ID": 2, "Type": "OtherNode", "x": 1, "y": 0, "z": 0}, ...
行分隔数组: https://www.example.com/nodes.jsonl
: https://www.example.com/nodes.jsonl
{"ID": 1, "Type": "Node", "x": 0, "y": 0, "z": 0}
{"ID": 2, "Type": "OtherNode", "x": 1, "y": 0, "z": 0}
...
我的课:
class Node
{
ulong ID { get; set; }
nodeType Type { get; set; }
decimal X { get; set; }
decimal Y { get; set; }
decimal Z { get; set; }
}
这些节点集合可能会变得非常大。 可能 GB 很大,但幸运的是每天只需要更新一次。 问题是,如果我让它异步下载 JSON,则在下载整个内容之前,该程序仍然无法使用。
WebClient.DownloadFile(settings.URL, path);
List<Node> nodes = JsonConvert.DeserializeObject<List<Node>>(path);
但是,如果我有前几个节点,我仍然可以在没有整个节点集的情况下开始求解网络。 如果我可以使用某种流一次一个字符地下载文件,我就可以绕过它。 使用行分隔格式我可以是这样的:
SomeStream someStream = new SomeStream(URL);
while(!someStream.eof)
{
string jsonString = someStream.ReadLine();
nodes.Add(JsonConvert.DeserializeObject<Node>(jsonString));
}
我担心除非网站支持一次请求一行数据,否则这可能是不可能的。 如果其他方法解决了这个问题,我仍然愿意学习。
我知道没有json 解析器有一个IAsyncEnumerbale
deseralizer(还)
但是,只要您不处理流,我们应该能够使用常规迭代器来执行此操作
public static IEnumerable<Node> ReadStream(Stream stream)
{
var serializer = new JsonSerializer();
using var reader = new StreamReader(stream);
using var jsonReader = new JsonTextReader(reader) {SupportMultipleContent = true};
while (jsonReader.Read())
yield return serializer.Deserialize<Node>(jsonReader);
}
例子
var httpclient = new HttpClient(); // dont do this, just an example
// note don't dispose the stream until its finished enumerating, or your will regret it
var stream = await httpclient.GetStreamAsync("https://www.example.com/nodes.json");
foreach (var item in ReadStream(stream))
Console.WriteLine(item.ID);
注意:这是完全未经测试的,因为我没有一个 url 可以让我连续输入 json 而不会乱七八糟地写一个
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.