我可以使用JavascriptSerializer反序列化为不可变对象吗?

使用System.Web.Script.Serialization.JavaScriptSerializer

我可以以某种方式反序列化为不可变对象吗?

  public class Item { public Uri ImageUri { get;private set; } public string Name { get; private set; } public Uri ItemPage { get;private set; } public decimal Retail { get;private set; } public int? Stock { get; private set; } public decimal Price { get; private set; } public Item(Uri imageUri, string name, Uri itemPage, decimal retail, int? stock, decimal price) { ImageUri = imageUri; Name = name; ItemPage = itemPage; Retail = retail; Stock = stock; Price = price; } } 

约束:我不想要一个公共的空构造函数,我不想将所有内容都改为mutable,而且我不想使用xml代替Json。

我必须找到答案,因为这是谷歌的第一个结果,但它没有给出一个例子,我决定分享我想出的东西(基于James Ellis-Jones提供的链接。)

我的情况是我需要一个“Money”对象是不可变的。 我的Money对象需要金额和货币。 需要是不可变的,因为我正在使用它,好像它是十进制值我正在替换它(数字操作支持类似的货币值)我需要传递它而不用担心我是否通过引用传递或者东西的副本。

所以,我在这里实现了JavaScriptConverter:

 public class MoneyJsonConverter : JavaScriptConverter { public override object Deserialize(IDictionary dictionary, Type type, JavaScriptSerializer serializer) { if (dictionary == null) throw new ArgumentNullException("dictionary"); if (type != typeof(Money)) return null; var amount = Convert.ToDecimal(dictionary.TryGet("Amount")); var currency = (string)dictionary.TryGet("Currency"); return new Money(currency, amount); } public override IDictionary Serialize(object obj, JavaScriptSerializer serializer) { var moneyAmount = obj as Money; if (moneyAmount == null) return new Dictionary(); var result = new Dictionary { { "Amount", moneyAmount.Amount }, { "Currency", moneyAmount.Currency }, }; return result; } public override IEnumerable SupportedTypes { get { return new ReadOnlyCollection(new List(new[] { typeof(Money) })); } } } 

然后我通过web.config文件在JavaScriptSerializer中注册了转换器:

            

而已! 我也用几个属性来装饰我的类,但是:

 [Serializable] [Immutable] public class Money 

JavaScriptSerializer提供了一个自定义API,您可以创建一个inheritance自JavaScriptConverter的类,以指定如何从字典构建您的Item类,然后在JavaScriptSerializer实例上使用RegisterConverters方法来注册您的自定义转换器。

javascriptserializer.registerconverters的定义