顯然,IDictionary<string,object>
被序列化爲KeyValuePair
對象的數組(例如,[{Key:"foo", Value:"bar"}, ...]
)。是否可以將其序列化爲對象(例如,{foo:"bar"}
)?使用JavaScriptSerializer序列化字典
回答
雖然我同意JavaScriptSerializer是廢話,Json.Net是一個更好的選擇,您可以使JavaScriptSerializer以您想要的方式序列化。 你將不得不註冊一個轉換器,並使用這樣的重寫Serialize方法:
public class KeyValuePairJsonConverter : JavaScriptConverter
{
public override object Deserialize(IDictionary<string, object> dictionary, Type type, JavaScriptSerializer serializer)
{
var instance = Activator.CreateInstance(type);
foreach (var p in instance.GetType().GetPublicProperties())
{
instance.GetType().GetProperty(p.Name).SetValue(instance, dictionary[p.Name], null);
dictionary.Remove(p.Name);
}
foreach (var item in dictionary)
(instance).Add(item.Key, item.Value);
return instance;
}
public override IDictionary<string, object> Serialize(object obj, JavaScriptSerializer serializer)
{
var result = new Dictionary<string, object>();
var dictionary = obj as IDictionary<string, object>;
foreach (var item in dictionary)
result.Add(item.Key, item.Value);
return result;
}
public override IEnumerable<Type> SupportedTypes
{
get
{
return new ReadOnlyCollection<Type>(new Type[] { typeof(your_type) });
}
}
}
JavaScriptSerializer javaScriptSerializer = new JavaScriptSerializer();
javaScriptSerializer.RegisterConverters(new JavaScriptConverter[] { new ExpandoJsonConverter() });
jsonOfTest = javaScriptSerializer.Serialize(test);
// {"x":"xvalue","y":"\/Date(1314108923000)\/"}
希望這有助於!
我想使用你的類,但它似乎你的'類對象'''實例'變量沒有添加方法。 –
不,這不可能與JavaScriptSerializer。這是可能的Json.NET:
public class Bar
{
public Bar()
{
Foos = new Dictionary<string, string>
{
{ "foo", "bar" }
};
}
public Dictionary<string, string> Foos { get; set; }
}
然後:
var bar = new Bar();
string json = JsonConvert.SerializeObject(bar, new KeyValuePairConverter());
產生所需:
{"Foos":{"foo":"bar"}}
我一開始就要走這條路。看到我以前的問題:http://stackoverflow.com/questions/6416017/json-net-deserializing-nested-dictionaries。我有一個使用Json.NET反序列化嵌套字典的問題。 – Daniel
@Daniel,Json.NET與'JavaScriptSerializer'相比是糖。所以,如果你在使用Json.NET時遇到問題,我不知道該怎麼說另一種方法:-)就你的其他問題而言,這是完全正常的行爲。您向串行器指出的所有內容都是字符串和對象的字典。所以你在代碼中使用弱類型的字典,你期待什麼?所有你當然可以得到的是一個弱類型的JObjects。使用一個強類型的字典:'Dictionary
你指的是什麼區別?我沒有看到它。 – Daniel
我能夠使用JavaScriptSerializer解決它,訣竅是創建自己的轉換器。下面的代碼工作代碼:
public class KeyValuePairJsonConverter : JavaScriptConverter {
public override object Deserialize(IDictionary<string, object> dictionary
, Type type
, JavaScriptSerializer serializer) {
throw new InvalidOperationException("Sorry, I do serializations only.");
}
public override IDictionary<string, object> Serialize(object obj, JavaScriptSerializer serializer) {
Dictionary<string, object> result = new Dictionary<string, object>();
Dictionary<string, MyClass> dictionaryInput = obj as Dictionary<string, MyClass>;
if (dictionaryInput == null) {
throw new InvalidOperationException("Object must be of Dictionary<string, MyClass> type.");
}
foreach (KeyValuePair<string, MyClass> pair in dictionaryInput)
result.Add(pair.Key, pair.Value);
return result;
}
public override IEnumerable<Type> SupportedTypes {
get {
return new ReadOnlyCollection<Type>(new Type[] { typeof(Dictionary<string, MyClass>) });
}
}
}
這裏是你如何使用它:
JavaScriptSerializer js = new JavaScriptSerializer();
js.RegisterConverters(new JavaScriptConverter[] { new KeyValuePairJsonConverter() });
Context.Response.Clear();
Context.Response.ContentType = "application/json";
Context.Response.Write(js.Serialize(myObject));
這裏有一個我相信從托馬斯的回答改進版本。奇蹟般有效。我們也可以爲ScriptIgnore屬性添加一個檢查,但是也可以自己敲一下。
順便說一下,我選擇了JavaScriptSerializer,因爲在我看來,第三方解決方案大部分時間都是這樣:不太知道,安裝時間長,經常被遺忘的先決條件和模糊的版權狀態,這使得它們在商業中分發風險更大。
P-S:我沒有理解爲什麼我們試圖將實例和實例反序列化爲字典,所以我剝去了這部分。
public class KeyValuePairJsonConverter : JavaScriptConverter
{
public override object Deserialize(IDictionary<string, object> deserializedJSObjectDictionary, Type targetType, JavaScriptSerializer javaScriptSerializer)
{
Object targetTypeInstance = Activator.CreateInstance(targetType);
FieldInfo[] targetTypeFields = targetType.GetFields(BindingFlags.Public | BindingFlags.Instance);
foreach (FieldInfo fieldInfo in targetTypeFields)
fieldInfo.SetValue(targetTypeInstance, deserializedJSObjectDictionary[fieldInfo.Name]);
return targetTypeInstance;
}
public override IDictionary<string, object> Serialize(Object objectToSerialize, JavaScriptSerializer javaScriptSerializer)
{
IDictionary<string, object> serializedObjectDictionary = new Dictionary<string, object>();
FieldInfo[] objectToSerializeTypeFields = objectToSerialize.GetType().GetFields(BindingFlags.Public | BindingFlags.Instance);
foreach (FieldInfo fieldInfo in objectToSerializeTypeFields)
serializedObjectDictionary.Add(fieldInfo.Name, fieldInfo.GetValue(objectToSerialize));
return serializedObjectDictionary;
}
public override IEnumerable<Type> SupportedTypes
{
get
{
return new ReadOnlyCollection<Type>(new Type[] { typeof(YOURCLASSNAME) });
}
}
}
關於我的PS筆記。也許這是爲了允許specidying通用字典類型,而不是類型,但老實說,我沒有看到指定通用字典類型的要點,因爲這整個事情是關於反序列化字典
我能夠解決JavaScriptSerializer LINQ的選擇:
var dictionary = new Dictionary<int, string>();
var jsonOutput = new JavaScriptSerializer().Serialize(dictionary.Select(x => new { Id = x.Key, DisplayText = x.Value }));
這在複雜情況下(即複雜的層次結構)不起作用,但它確實解決了這個問題,因此如果您想避免向JavaScriptSerializer或第三方庫添加樣板文件,這是一個解決方案。 –
對於我來說,即使在複雜的情況下,它也可以工作,只需更改爲'.Serialize(dictionary)'。它更簡單,然後JsonConvert,準備使用。我希望我能給+2這個答案 –
- 1. 使用JavaScriptSerializer反序列化JSON字典列表
- 2. VB.NET JavaScriptSerializer()反序列化字典數組成員
- 3. 使用泛型與JavaScriptSerializer反序列化
- 4. 使用JavaScriptSerializer C反序列化JSON#
- 5. 使用JavaScriptSerializer反序列化JSON文件()
- 6. JavaScriptSerializer上反序列化
- 7. MVC JavaScriptSerializer反序列化JSON
- 8. 如何使用JavascriptSerializer反序列化C#中的json字符串
- 9. 使用JavaScriptSerializer進行反序列化時缺少字段
- 10. 使用JSON.NET反序列化字典
- 11. JSON序列化/反序列化爲包含字典的字典
- 12. 序列化列表/字典
- 13. 使用JSON JavaScriptSerializer進行序列化或反序列化時出錯。
- 14. 使用JSON JavaScriptSerializer進行序列化或反序列化時出錯
- 15. 序列化字典JSON
- 16. 序列化字典到XML
- 17. 序列化Cookie字典?
- 18. 序列化字典爲JSON
- 19. 推出序列化字典
- 20. C#字典反序列化
- 21. XML序列化字典
- 22. 如何使用Json.Net使用自定義鍵序列化/反序列化字典?
- 23. JavaScriptSerializer非反序列化DateTime/TimeSpan正確
- 24. JavaScriptSerializer反序列化拋出System.OutOfMemoryException
- 25. C#JavaScriptSerializer JSON數組反序列化
- 26. JavaScriptSerializer()序列化:PascalCase到駝峯
- 27. 使用JSON.NET反序列化和序列化字典<字符串,對象>
- 28. 在C#中使用JSON.NET或JavaScriptSerializer反序列化JSON對象
- 29. Json.Encode()是否使用JavaScriptSerializer類來序列化
- 30. 使用JavaScriptSerializer反序列化JSON片段ASP.NET
是,不使用JavaScriptSerializer,它完全扯淡。使用Newtonsoft Json.NET –