c# - Deserializar el objeto json en un objeto dinámico utilizando Json.net
(8)
¿Es posible devolver un objeto dinámico desde una deserialización json utilizando json.net? Me gustaría hacer algo como esto:
dynamic jsonResponse = JsonConvert.Deserialize(json);
Console.WriteLine(jsonResponse.message);
A partir de la versión 1 de Json.NET 4.0, hay soporte dinámico nativo:
[Test]
public void DynamicDeserialization()
{
dynamic jsonResponse = JsonConvert.DeserializeObject("{/"message/":/"Hi/"}");
jsonResponse.Works = true;
Console.WriteLine(jsonResponse.message); // Hi
Console.WriteLine(jsonResponse.Works); // True
Console.WriteLine(JsonConvert.SerializeObject(jsonResponse)); // {"message":"Hi","Works":true}
Assert.That(jsonResponse, Is.InstanceOf<dynamic>());
Assert.That(jsonResponse, Is.TypeOf<JObject>());
}
Y, por supuesto, la mejor manera de obtener la versión actual es a través de NuGet.
Actualizado (11/12/2014) para abordar comentarios:
Esto funciona perfectamente bien. Si inspecciona el tipo en el depurador, verá que el valor es, de hecho, dinámico . El tipo subyacente es un objeto JObject
. Si desea controlar el tipo (como especificar ExpandoObject
, hágalo).
Sé que esta es una publicación antigua, pero JsonConvert en realidad tiene un método diferente, así que sería
var product = new { Name = "", Price = 0 };
var jsonResponse = JsonConvert.DeserializeAnonymousType(json, product);
Sí, es posible. He estado haciendo eso todo el tiempo.
dynamic Obj = JsonConvert.DeserializeObject(<your json string>);
Es un poco más complicado para el tipo no nativo. Supongamos que dentro de su Obj, hay objetos ClassA y ClassB. Todos ellos se convierten a JObject. Lo que necesitas hacer es:
ClassA ObjA = Obj.ObjA.ToObject<ClassA>();
ClassB ObjB = Obj.ObjB.ToObject<ClassB>();
Sí, puede hacerlo utilizando JsonConvert.DeserializeObject. Para hacer eso, simplemente hazlo:
dynamic jsonResponse = JsonConvert.DeserializeObject(json);
Console.WriteLine(jsonResponse["message"]);
Si solo deserializa a dinámico, obtendrás un JObject de vuelta. Puedes obtener lo que quieras usando un ExpandoObject.
var converter = new ExpandoObjectConverter();
dynamic message = JsonConvert.DeserializeObject<ExpandoObject>(jsonString, converter);
Si usa JSON.NET con una versión anterior que no fue JObject.
Esta es otra forma sencilla de crear un objeto dinámico desde JSON: https://github.com/chsword/jdynamic
Instalación de NuGet
PM> Install-Package JDynamic
Apoyo utilizando índice de cadena para acceder a miembros como:
dynamic json = new JDynamic("{a:{a:1}}");
Assert.AreEqual(1, json["a"]["a"]);
Caso de prueba
Y puedes usar este util como sigue:
Obtener el valor directamente
dynamic json = new JDynamic("1");
//json.Value
2. Obtener el miembro en el objeto json
dynamic json = new JDynamic("{a:''abc''}");
//json.a is a string "abc"
dynamic json = new JDynamic("{a:3.1416}");
//json.a is 3.1416m
dynamic json = new JDynamic("{a:1}");
//json.a is integer: 1
3.IEnumerable
dynamic json = new JDynamic("[1,2,3]");
/json.Length/json.Count is 3
//And you can use json[0]/ json[2] to get the elements
dynamic json = new JDynamic("{a:[1,2,3]}");
//json.a.Length /json.a.Count is 3.
//And you can use json.a[0]/ json.a[2] to get the elements
dynamic json = new JDynamic("[{b:1},{c:1}]");
//json.Length/json.Count is 2.
//And you can use the json[0].b/json[1].c to get the num.
Otro
dynamic json = new JDynamic("{a:{a:1} }");
//json.a.a is 1.
la última versión de json.net permite hacer esto:
dynamic d = JObject.Parse("{number:1000, str:''string'', array: [1,2,3,4,5,6]}");
Console.WriteLine(d.number);
Console.WriteLine(d.str);
Console.WriteLine(d.array.Count);
salida:
1000
string
6
Documentación aquí: LINQ to JSON con Json.NET
Nota: En el momento en que respondí esta pregunta en 2010, no había manera de deserializar sin algún tipo de tipo, esto le permitía deserializar sin tener que definir la clase real y permitir que se usara una clase anónima para realizar la deserialización.
Necesita tener algún tipo de tipo para deserializar. Podrías hacer algo en la línea de:
var product = new { Name = "", Price = 0 };
dynamic jsonResponse = JsonConvert.Deserialize(json, product.GetType());
Mi respuesta se basa en una solución para la compilación de .NET 4.0 en el serializador JSON. El enlace para deserializar a tipos anónimos está aquí: