C#中System.Text.Json匿名对象反序列化

 更新时间:2023年05月25日 08:22:14   作者:波多尔斯基  
这篇文章主要介绍了System.Text.Json匿名对象反序列化,下文代码基于. NET 6,为了代码整洁,实际配置了PropertyNameCaseInsensitive = true,本文结合实例代码介绍的非常详细,需要的朋友可以参考下

以前就是一直使用 Newtonsoft.Json 用起来还是挺舒服的。由于 JSON 的应用越来越广,现在. NET Core 都内置了 System.Text.Json 可以直接对 JSON 进行操作,不过两个东西的体验依然有点区别。

有时候我们会遇到的从第三方传递过来的 json string 对象,对其进行解析并不需要所有的字段,只需要一个目标的字段时,可以考虑使用匿名对象/动态对象对其反序列化。

之前的 Newtonsoft.Json 好像直接使用 dynamic,运用 JObject 进行处理,现在的不是那么容易。下文代码基于. NET 6,为了代码整洁,实际配置了 PropertyNameCaseInsensitive = true,但是下面代码中并没有体现。

数据

我们定义了如下的类型,并从 OData 获得了 str 字符串型数据。

public readonly static string str = """
        {"@odata.context":"http://localhost:9000/api/v1/$metadata#DataDto","value":[{"id":"0b734ed7-2955-4af4-a902-35dc17871094","timestamp":1684839865920},{"id":"7e285d08-cdb3-4209-8335-0ff9b20d39ef","timestamp":1684836312421}]}
        """;
    public class DataDto
    {
        public string? Id { get; set; }
        public long Timestamp { get; set; }
    }

由于有元数据,我们无法直接将上面的字符串反序列化为 DataDto 的列表对象。

自定义类

最简单的方式,是对应此类对象,设计一个只用于反序列化的新类。

    public class ODataEnumerableResultWrapper<T>
        where T : class
    {
        public IEnumerable<T> Value { get; set; }
    }
	var meta = JsonSerializer.Deserialize<ODataEnumerableResultWrapper<DataDto>>(str);
	var target = meta.Value;

匿名方式

可以使用 JsonNode 来直接反序列化,并使用类似键值对的形式访问。

    public static void Main() {
        JsonNode? meta = JsonSerializer.Deserialize<JsonNode>(str);
        //如果直接是简单的对象,而不是数组,可以使用GetValue<T>这种形式。
        var count = meta?["value"]?.Deserialize<IEnumerable<DataDto>>().Count();
        Console.WriteLine(count);
    }
}

注意,这样的操作和你反序列化为 JsonDocument/JsonElement 并没有什么本质的区别。

动态方式

由于设计区别,直接使用 dynamic 进行反序列化,得到的对象并不具有一般 dynamic 的性质(实际上是 System.Text.Json.JsonElement 对象)。因此,我们无法通过的 dynamic 访问成员的形式进行操作。

dynamic meta = JsonSerializer.Deserialize<dynamic>(str);
Console.WriteLine(meta.GetType());
//OUTPUT: System.Text.Json.JsonElement

有 文章 说可以使用 ExpandoOject 实现,但是实际上无法对子级对象进行类似的访问,因为获取的子级对象,实际上是 JsonElement

        dynamic meta = JsonSerializer.Deserialize<System.Dynamic.ExpandoObject>(str);
        Console.WriteLine(meta.GetType());
        //System.Dynamic.ExpandoObject
        Console.WriteLine(meta.value);
        //[{"id":"0b734ed7-2955-4af4-a902-35dc17871094","timestamp":1684839865920},{"id":"7e285d08-cdb3-4209-8335-0ff9b20d39ef","timestamp":1684836312421}]
        Console.WriteLine(meta.value.GetType());
        //System.Text.Json.JsonElement

当然可以通过自定义序列化的方式操作(见参考),但是这个办法与我们的不写额外代码的初衷相冲突,因此不考虑了。

参考

到此这篇关于System.Text.Json匿名对象反序列化的文章就介绍到这了,更多相关System.Text.Json反序列化内容请搜索脚本之家以前的文章或继续浏览下面的相关文章希望大家以后多多支持脚本之家!

相关文章

  • C# Replace替换的具体使用

    C# Replace替换的具体使用

    本文主要介绍了C# Replace替换的具体使用,文中通过示例代码介绍的非常详细,对大家的学习或者工作具有一定的参考学习价值,需要的朋友们下面随着小编来一起学习学习吧
    2023-02-02
  • c#实现服务器性能监控并发送邮件保存日志

    c#实现服务器性能监控并发送邮件保存日志

    这篇文章主要介绍了c#实现服务器性能监控并发送邮件保存日志的示例,代码分为客户端和服务端,客户端可安装为本地服务形式启动
    2014-01-01
  • C#取得随机颜色的方法

    C#取得随机颜色的方法

    这篇文章主要介绍了C#取得随机颜色的方法,通过自定义函数实现随机颜色的功能,非常具有实用价值,需要的朋友可以参考下
    2015-01-01
  • 基于C#实现12306的动态验证码变成静态验证码的方法

    基于C#实现12306的动态验证码变成静态验证码的方法

    这篇文章主要介绍了基于C#实现12306的动态验证码变成静态验证码的方法的相关资料,需要的朋友可以参考下
    2015-12-12
  • C#如何防止程序多次运行的技巧

    C#如何防止程序多次运行的技巧

    这篇文章主要为大家详细介绍了C#如何防止程序多次运行的技巧,供大家参考,感兴趣的小伙伴们可以参考一下
    2016-04-04
  • C#获取网页HTML源码实例

    C#获取网页HTML源码实例

    这篇文章主要介绍了C#获取网页HTML源码的方法,是非常实用的技巧,需要的朋友可以参考下
    2014-10-10
  • C#实现单位换算器

    C#实现单位换算器

    这篇文章主要为大家详细介绍了C#实现单位换算器,文中示例代码介绍的非常详细,具有一定的参考价值,感兴趣的小伙伴们可以参考一下
    2022-01-01
  • C#实现程序等待延迟执行的方法

    C#实现程序等待延迟执行的方法

    这篇文章主要介绍了C#实现程序等待延迟执行的方法,涉及C#动态链接库的使用及延迟的实现技巧,需要的朋友可以参考下
    2015-09-09
  • C#函数式编程中的递归调用之尾递归详解

    C#函数式编程中的递归调用之尾递归详解

    这篇文章主要介绍了C#函数式编程中的递归调用详解,本文讲解了什么是尾递归、尾递归的多种方式、尾递归的代码实例等内容,需要的朋友可以参考下
    2015-01-01
  • c#计算某段代码的执行时间实例方法

    c#计算某段代码的执行时间实例方法

    在本篇文章里我们给大家整理了关于c#计算某段代码的执行时间的方法和经验,有兴趣的朋友们学习下。
    2019-02-02

最新评论