C # JSON Serialización del diccionario en {key: value, …} en lugar de {key: key, value: value, …}

¿Es posible serializar un .Net Dictionary en JSON con DataContractJsonSerializer que tiene el formato:

{ key0:value0, key1:value1, ... } 

Utilizo Dictionary porque no hay una estructura predefinida de las entradas.

¡Estoy interesado solo por el resultado de DataContractJsonSerializer ! Ya encontré un ejemplo “Surrogate”, pero hay un “dato” adicional en el resultado, y si el diccionario es , el escape también es falso.


Encontré la solución, ¡qué necesidad! Antes que nada, una clase serializable de “diccionario”: (Por supuesto, esta muestra funciona solo de una manera, pero no necesito deserialización)

 [Serializable] public class MyJsonDictionary : ISerializable { Dictionary dict = new Dictionary(); public MyJsonDictionary() { } protected MyJsonDictionary( SerializationInfo info, StreamingContext context ) { throw new NotImplementedException(); } public void GetObjectData( SerializationInfo info, StreamingContext context ) { foreach( K key in dict.Keys ) { info.AddValue( key.ToString(), dict[ key ] ); } } public void Add( K key, V value ) { dict.Add( key, value ); } public V this[ K index ] { set { dict[ index ] = value; } get { return dict[ index ]; } } } 

Uso:

 public class MainClass { public static String Serialize( Object data ) { var serializer = new DataContractJsonSerializer( data.GetType() ); var ms = new MemoryStream(); serializer.WriteObject( ms, data ); return Encoding.UTF8.GetString( ms.ToArray() ); } public static void Main() { MyJsonDictionary result = new MyJsonDictionary(); result["foo"] = "bar"; result["Name"] = "John Doe"; result["Age"] = 32; MyJsonDictionary address = new MyJsonDictionary(); result["Address"] = address; address["Street"] = "30 Rockefeller Plaza"; address["City"] = "New York City"; address["State"] = "NY"; Console.WriteLine( Serialize( result ) ); Console.ReadLine(); } } 

Y el resultado:

 { "foo":"bar", "Name":"John Doe", "Age":32, "Address":{ "__type":"MyJsonDictionaryOfstringanyType:#Json_Dictionary_Test", "Street":"30 Rockefeller Plaza", "City":"New York City", "State":"NY" } } 

Json.NET hace esto …

 Dictionary values = new Dictionary(); values.Add("key1", "value1"); values.Add("key2", "value2"); string json = JsonConvert.SerializeObject(values); // { // "key1": "value1", // "key2": "value2" // } 

Más ejemplos: serializar colecciones con Json.NET

use la propiedad UseSimpleDictionaryFormat en DataContractJsonSerializer y UseSimpleDictionaryFormat en true .

Hace el trabajo 🙂

Estoy usando MVC4 de fábrica con este código ( ToDictionary en los dos parámetros dentro de ToDictionary )

  var result = new JsonResult() { Data = new { partials = GetPartials(data.Partials).ToDictionary(x => x.Key, y=> y.Value) } }; 

Obtengo lo que se espera:

 {"partials":{"cartSummary":"\u003cb\u003eCART SUMMARY\u003c/b\u003e"}} 

Importante : WebAPI en MVC4 utiliza la serialización de JSON.NET de fábrica, pero el resultado de la acción de JsonResult web estándar no. Por lo tanto, recomiendo usar un ActionResult personalizado para forzar la serialización de JSON.NET. También puede obtener un buen formato

Aquí hay un resultado de JsonNetResult simple JsonNetResult

http://james.newtonking.com/archive/2008/10/16/asp-net-mvc-and-json-net.aspx

Verá la diferencia (y puede asegurarse de estar utilizando la correcta) al serializar una fecha:

Manera de Microsoft:

  {"wireTime":"\/Date(1355627201572)\/"} 

JSON.NET manera:

  {"wireTime":"2012-12-15T19:07:03.5247384-08:00"} 

Desafortunadamente, esto no es posible actualmente en la última versión de DataContractJsonSerializer. Ver: http://connect.microsoft.com/VisualStudio/feedback/details/558686/datacontractjsonserializer-should-serialize-dictionary-kv-as-a-json-associative-array

La solución alternativa sugerida actualmente es usar el JavaScriptSerializer como Mark sugerido anteriormente.

¡Buena suerte!

La clase MyJsonDictionary funcionó bien para mí, EXCEPTO que la salida resultante está codificada en XML, por lo que “0” se convierte en “0030 “. Actualmente estoy atrapado en .NET 3.5, al igual que muchos otros, por lo que muchas de las otras soluciones no están disponibles para mí. “Convierte las imágenes” al revés y se dio cuenta de que nunca podría convencer a Microsoft para que me diera el formato que quería, pero …

string json = XmlConvert.DecodeName (xmlencodedJson);

¡TADA!

El resultado es lo que esperaría ver: encoding regular legible por humanos y no XML. Funciona en .NET 3.5.