Newtonsoft Json.NET动态决定属性是否序列化

2024-02-21 03:08

本文主要是介绍Newtonsoft Json.NET动态决定属性是否序列化,希望对大家解决编程问题提供一定的参考价值,需要的开发者们随着小编来一起学习吧!

转自:http://www.it165.net/pro/html/201309/7044.html

本人用了,解决了现实的业务问题。


昨天提到Json.NET属性序列化设定,接获读者森哥留言:

请问黑大,
针对不需要序列化的「属性」是否可以透过程序「动态」设定或是过滤?

有预感迟早也会遇到这个靠杯火杯的考验,决定打铁趁热,马上来练习。所幸,Json.NET真的很强大,早就料想到此一需求,提供ContractResolver以实现神乎奇技的高度动态化。

我写了一个范例,展示两种动态决定应序列化属性的情境:

Serialize时传入属性名称数组作为参数,正向表列JSON应包含的属性。
由对象属性值决定属性是否要序列化,例如: 如果是女生就不包含年龄。(这几乎已弹性到极点,虽然实务上不常用到)
程序的做法是宣告两个继承自DefaultContractResolver的类别: LimitPropsContractResolver在建构时传入string[]参数列出要序列化的属性名称,并覆写CreateProperties方法,过滤base.CreateProperties()传回的IList<JsonProperty>,只保留前述string[]有列出的属性;HideAgeContractResolver则覆写CreateProperty()方法,由base.CreateProperty()取得JsonProperty,JsonProperty有个ShouldSerialize属性可以传入Lambda表达式,逐笔处理每个要序列化的对象,在Lambda表达式中可将对象转型为原型别进行判断,若不要序列化就传回false。 www.it165.net

 

view source print ?
01. using System;
02. using System.Collections.Generic;
03. using System.Linq;
04. using System.Reflection;
05. using System.Text;
06. using Newtonsoft.Json;
07. using Newtonsoft.Json.Converters;
08. using Newtonsoft.Json.Serialization;
09.  
10. namespace ConsoleApplication1
11. {
12. class Program
13. {
14. public enum Gender
15. {
16. Male, Female
17. }
18.  
19. public class Person
20. {
21. public string Name { getset; }
22. [JsonConverter(typeof(StringEnumConverter))]
23. public Gender Gender { getset; }
24. public int Age { getset; }
25. public Person(string name, Gender gender, int age)
26. {
27. Name = name; Gender = gender; Age = age;
28. }
29. }
30.  
31. public class HideAgeContractResolver : DefaultContractResolver
32. {
33. //REF: http://james.newtonking.com/projects/json/help/index.html?topic=html/ContractResolver.htm
34. protected override JsonProperty CreateProperty(MemberInfo member,
35. MemberSerialization memberSerialization)
36. {
37. JsonProperty p = base.CreateProperty(member, memberSerialization);
38. if (p.PropertyName == "Age")
39. {
40. //依性别决定是否要序列化
41. p.ShouldSerialize = instance =>
42. {
43. Person person = (Person)instance;
44. return person.Gender == Gender.Male;
45. };
46. }
47. return p;
48. }
49. }
50.  
51. public class LimitPropsContractResolver : DefaultContractResolver
52. {
53. string[] props = null;
54. public LimitPropsContractResolver(string[] props)
55. {
56. //指定要序列化属性的清单
57. this.props = props;
58. }
59. //REF: http://james.newtonking.com/archive/2009/10/23/efficient-json-with-json-net-reducing-serialized-json-size.aspx
60. protected override IList<JsonProperty> CreateProperties(Type type,
61. MemberSerialization memberSerialization)
62. {
63. IList<JsonProperty> list =
64. base.CreateProperties(type, memberSerialization);
65. //只保留清单有列出的属性
66. return list.Where(p => props.Contains(p.PropertyName)).ToList();
67. }
68.  
69. }
70.  
71. static void Main(string[] args)
72. {
73. List<Person> list = new List<Person>();
74. list.Add(new Person("George", Gender.Male, 18));
75. list.Add(new Person("Mary", Gender.Female, 40));
76. //正常输出
77. Console.WriteLine(JsonConvert.SerializeObject(
78. list, Formatting.Indented));
79. var settings = new JsonSerializerSettings();
80. //加上ContractResolver,正向表列哪些属性要序列化
81. settings.ContractResolver =
82. new LimitPropsContractResolver("Name,Age".Split(','));
83. Console.WriteLine(JsonConvert.SerializeObject(
84. list, Formatting.Indented, settings));
85. //加上ContractResolver,依对象的属性值动态决定要不要序列化
86. settings.ContractResolver = new HideAgeContractResolver();
87. Console.WriteLine(JsonConvert.SerializeObject(
88. list, Formatting.Indented, settings));
89. Console.ReadLine();
90.  
91. }
92. }
93. }

程序执行结果如下,共有三段输出,第一段为正常版;第二段套用LimitPropsContractResolver("Name,Age".Split(',')),故JSON中只见Name及Age,Gender被隐藏;第三段套用了HideAgeContractResolver(),如结果所示,Mary的JSON内容不包含年龄,George则包含。

 

view source print ?
01. [
02. {
03. "Name""George",
04. "Gender""Male",
05. "Age": 18
06. },
07. {
08. "Name""Mary",
09. "Gender""Female",
10. "Age": 40
11. }
12. ]
13. [
14. {
15. "Name""George",
16. "Age": 18
17. },
18. {
19. "Name""Mary",
20. "Age": 40
21. }
22. ]
23. [
24. {
25. "Name""George",
26. "Gender""Male",
27. "Age": 18
28. },
29. {
30. "Name""Mary",
31. "Gender""Female"
32. }
33. ]

演练完毕,内心激动澎湃,对Json.NET的景仰如淊淊江水,绵绵不绝~

如果奥斯卡有最佳组件奖,我提名它!


这篇关于Newtonsoft Json.NET动态决定属性是否序列化的文章就介绍到这儿,希望我们推荐的文章对编程师们有所帮助!



http://www.chinasem.cn/article/730391

相关文章

springboot使用Scheduling实现动态增删启停定时任务教程

《springboot使用Scheduling实现动态增删启停定时任务教程》:本文主要介绍springboot使用Scheduling实现动态增删启停定时任务教程,具有很好的参考价值,希望对大家有... 目录1、配置定时任务需要的线程池2、创建ScheduledFuture的包装类3、注册定时任务,增加、删

MySQL 中的 JSON 查询案例详解

《MySQL中的JSON查询案例详解》:本文主要介绍MySQL的JSON查询的相关知识,本文给大家介绍的非常详细,对大家的学习或工作具有一定的参考借鉴价值,需要的朋友参考下吧... 目录mysql 的 jsON 路径格式基本结构路径组件详解特殊语法元素实际示例简单路径复杂路径简写操作符注意MySQL 的 J

Spring Boot中JSON数值溢出问题从报错到优雅解决办法

《SpringBoot中JSON数值溢出问题从报错到优雅解决办法》:本文主要介绍SpringBoot中JSON数值溢出问题从报错到优雅的解决办法,通过修改字段类型为Long、添加全局异常处理和... 目录一、问题背景:为什么我的接口突然报错了?二、为什么会发生这个错误?1. Java 数据类型的“容量”限制

SpringBoot基于配置实现短信服务策略的动态切换

《SpringBoot基于配置实现短信服务策略的动态切换》这篇文章主要为大家详细介绍了SpringBoot在接入多个短信服务商(如阿里云、腾讯云、华为云)后,如何根据配置或环境切换使用不同的服务商,需... 目录目标功能示例配置(application.yml)配置类绑定短信发送策略接口示例:阿里云 & 腾

Spring 请求之传递 JSON 数据的操作方法

《Spring请求之传递JSON数据的操作方法》JSON就是一种数据格式,有自己的格式和语法,使用文本表示一个对象或数组的信息,因此JSON本质是字符串,主要负责在不同的语言中数据传递和交换,这... 目录jsON 概念JSON 语法JSON 的语法JSON 的两种结构JSON 字符串和 Java 对象互转

Python如何精准判断某个进程是否在运行

《Python如何精准判断某个进程是否在运行》这篇文章主要为大家详细介绍了Python如何精准判断某个进程是否在运行,本文为大家整理了3种方法并进行了对比,有需要的小伙伴可以跟随小编一起学习一下... 目录一、为什么需要判断进程是否存在二、方法1:用psutil库(推荐)三、方法2:用os.system调用

C++如何通过Qt反射机制实现数据类序列化

《C++如何通过Qt反射机制实现数据类序列化》在C++工程中经常需要使用数据类,并对数据类进行存储、打印、调试等操作,所以本文就来聊聊C++如何通过Qt反射机制实现数据类序列化吧... 目录设计预期设计思路代码实现使用方法在 C++ 工程中经常需要使用数据类,并对数据类进行存储、打印、调试等操作。由于数据类

Python中判断对象是否为空的方法

《Python中判断对象是否为空的方法》在Python开发中,判断对象是否为“空”是高频操作,但看似简单的需求却暗藏玄机,从None到空容器,从零值到自定义对象的“假值”状态,不同场景下的“空”需要精... 目录一、python中的“空”值体系二、精准判定方法对比三、常见误区解析四、进阶处理技巧五、性能优化

MySQL 中查询 VARCHAR 类型 JSON 数据的问题记录

《MySQL中查询VARCHAR类型JSON数据的问题记录》在数据库设计中,有时我们会将JSON数据存储在VARCHAR或TEXT类型字段中,本文将详细介绍如何在MySQL中有效查询存储为V... 目录一、问题背景二、mysql jsON 函数2.1 常用 JSON 函数三、查询示例3.1 基本查询3.2

MySQL中动态生成SQL语句去掉所有字段的空格的操作方法

《MySQL中动态生成SQL语句去掉所有字段的空格的操作方法》在数据库管理过程中,我们常常会遇到需要对表中字段进行清洗和整理的情况,本文将详细介绍如何在MySQL中动态生成SQL语句来去掉所有字段的空... 目录在mysql中动态生成SQL语句去掉所有字段的空格准备工作原理分析动态生成SQL语句在MySQL