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

前端之家收集整理的这篇文章主要介绍了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

01. usingSystem;
02. System.Collections.Generic;
03. System.Linq;
04. System.Reflection;
05. System.Text;
06. Newtonsoft.Json;
07. Newtonsoft.Json.Converters;
08. Newtonsoft.Json.Serialization;
09.
10. namespaceConsoleApplication1
11. {
12. classProgram
13. 14. publicenumGender
15. 16. Male,Female
17. }
18.
19. Person
20. {
21. stringName {get;set; }
22. [JsonConverter(typeof(StringEnumConverter))]
23. publicGender Gender {24. intAge {; }
25. Person(name,Gender gender,age)
26. 27. Name = name; Gender = gender; Age = age;
28. }
29. 30. 31. HideAgeContractResolver : DefaultContractResolver
34. protectedoverrideJsonProperty 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. returnperson.Gender == Gender.Male;
45. };
46. 47. p;
48. 49. 50. 51. LimitPropsContractResolver : DefaultContractResolver
52. 53. [] props =null;
54. LimitPropsContractResolver([] props)
55. 56. //指定要序列化属性的清单
57. this.props = props;
60. IList<JsonProperty> CreateProperties(Type type,92); background:none">61. 62. 63. IList<JsonProperty> list =
64. .CreateProperties(type,memberSerialization);
65. //只保留清单有列出的属性
66. list.Where(p => props.Contains(p.PropertyName)).ToList();
67. 68. 69. 70. 71. staticvoidMain([] args)
72. 73. List<Person> list =newList<Person>();
74. list.Add(Person("George",Gender.Male,18));
75. "Mary" 76. //正常输出
77. Console.WriteLine(JsonConvert.SerializeObject(
78. list,Formatting.Indented));
79. var settings =JsonSerializerSettings();
80. //加上ContractResolver,正向表列哪些属性要序列化
81. settings.ContractResolver =
82. LimitPropsContractResolver("Name,Age".Split(','));
83. 84. 85. //加上ContractResolver,依对象的属性值动态决定要不要序列化
86. settings.ContractResolver =HideAgeContractResolver();
87. 88. 89. Console.ReadLine();
90. 91. 92. 93. }

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

[
"Name": "Gender""Male": 18
},宋体; background:none">"Female": 40
]
: 18
"Female"
]

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

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

猜你在找的Json相关文章