Como você sugere que o stackOverflow feche uma pergunta como "muito antiga"? Faz seis anos, há respostas válidas e sugestões razoáveis para todas as versões do .net desde então ... tantas que não são mais úteis.
andrew lorien
Respostas:
546
O Json.NET nos permite fazer isso:
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);
Observe que para matrizes a sintaxe é JArray.Parse.
Jgillich 15/05
4
Por que precisamos usar a palavra dinâmica? Estou com medo de nunca ter usado antes: D
MonsterMMORPG
3
No VB.Net você precisa fazer #Dim d As Object = JObject.Parse("{number:1000, str:'string', array: [1,2,3,4,5,6]}")
ilans
2
@MonsterMMORPG Você deveria ser :) Dinâmico é um anti-padrão em quase todas as circunstâncias, mas, de vez em quando, você pode ter uma situação em que é razoável usá-lo.
Pluc 18/03/16
4
Com Newtonsoft.Json 8.0.3 (.NET 4.5.2): Microsoft.CSharp.RuntimeBinder.RuntimeBinderException ocorreu HResult = -2146233088 Mensagem = 'Newtonsoft.Json.Linq.JObject' não contém uma definição para 'number' Source = Microsoft .CSharp StackTrace: no Microsoft.CSharp.RuntimeBinder.RuntimeBinderController.SubmitError (CError pError)
user4698855
107
A partir do Json.NET 4.0 Release 1, há suporte dinâmico nativo:
E, é claro, a melhor maneira de obter a versão atual é via NuGet.
Atualizado (11/12/2014) para tratar dos comentários:
Isso funciona perfeitamente bem. Se você inspecionar o tipo no depurador, verá que o valor é de fato dinâmico . O tipo subjacente é a JObject. Se você deseja controlar o tipo (como especificar ExpandoObject, faça-o).
Isso nunca parece funcionar. Ele retorna apenas um JObject, não uma variável dinâmica.
Paul
12
BTW, isso funciona: JsonConvert.DeserializeObject <ExpandoObject> (STRING); com desserialização adequada, para que não tenhamos JObject etc.
Gutek
2
@Gutek não sabe qual é o seu problema. Você executou o código? Adicionei declarações ao teste e adicionei uma propriedade que não está no json original. Captura de tela do depurador incluída.
22814 David Peden
1
@DavidPeden se você tiver JObject e tentará vincular isso no Razor, obterá exceções. A pergunta era sobre desserialização para objeto dinâmico - JObject é dinâmico, mas contém tipos "próprios", como JValue, e não tipos primitivos. Não posso usar o @Model.Propnome no Razor se o tipo de retorno for JValue.
Gutek
2
Isso funciona, mas cada propriedade dinâmica é a JValue. O que me confundiu porque eu estava trabalhando na janela do depurador / janela imediata e não estava vendo apenas strings. David mostra isso na captura de tela inferior. A JValueé conversível para que você pode apenas fazerstring m = jsonResponse.message
Luke Puplett
66
Se você apenas desserializar para dinâmico, receberá um JObject de volta. Você pode obter o que deseja usando um ExpandoObject.
var converter =newExpandoObjectConverter();dynamic message =JsonConvert.DeserializeObject<ExpandoObject>(jsonString, converter);
Isso seria desserializar uma carga útil do json para um tipo anônimo, não dinâmico. Tipos anônimos e tipos dinâmicos são coisas diferentes, e não acredito que isso atenda à pergunta.
jrista
1
É necessário usar duas variáveis? Por que não reutilizar o primeiro na segunda declaração?
RenniePet
21
Sim, você pode fazer isso usando o JsonConvert.DeserializeObject. Para fazer isso, basta fazer:
JsonConvertnão contém um método chamado Deserialize.
Can Poyrazoğlu
ele deve ser apenas DeserializeObject, mas isso deve ser a resposta aceita IMO
superjugy
21
Nota: No momento em que respondi a essa pergunta em 2010, não havia como desserializar sem algum tipo, isso permitiu que você desserializasse sem precisar definir a classe real e permitir que uma classe anônima fosse usada para fazer a desserialização.
Você precisa ter algum tipo de tipo para desserializar. Você poderia fazer algo como:
var product =new{Name="",Price=0};dynamic jsonResponse =JsonConvert.Deserialize(json, product.GetType());
Minha resposta é baseada em uma solução para compilação do .NET 4.0 no serializador JSON. O link para desserializar para tipos anônimos está aqui:
Estou com você e não sei por que as pessoas votam menos, se alguém pode, por favor .. por favor, explique por quê?
PEO
18
Eles estão com voto negativo porque a questão é desserializar sem um tipo.
Richard
4
A resposta era válida no momento em que foi escrita em 2010, quando não havia outra solução. Foi até a resposta aceita por um pequeno período de tempo até o suporte no JSON.NET.
6776 Phill
1
Isso não produz um objeto dinâmico. Isso produz um JObject que você faz referência como dinâmica. Mas ainda é um objeto dentro.
ghostbust555
5
Se você usa o JSON.NET com a versão antiga que não JObject.
E você pode usar este utilitário da seguinte maneira:
Obtenha o valor diretamente
dynamic json =newJDynamic("1");//json.Value
2.Obtenha o membro no objeto json
dynamic json =newJDynamic("{a:'abc'}");//json.a is a string "abc"dynamic json =newJDynamic("{a:3.1416}");//json.a is 3.1416mdynamic json =newJDynamic("{a:1}");//json.a is integer: 1
3.IEnumerable
dynamic json =newJDynamic("[1,2,3]");/json.Length/json.Countis3//And you can use json[0]/ json[2] to get the elementsdynamic json =newJDynamic("{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 elementsdynamic json =newJDynamic("[{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.
De outros
dynamic json =newJDynamic("{a:{a:1} }");//json.a.a is 1.
É um pouco mais complicado para o tipo não nativo. Suponha que dentro do seu Obj, haja objetos ClassA e ClassB. Todos eles são convertidos em JObject. O que você precisa fazer é:
Respostas:
O Json.NET nos permite fazer isso:
Resultado:
Documentação aqui: LINQ to JSON com Json.NET
Consulte também JObject.Parse e JArray.Parse
fonte
JArray.Parse
.Dim d As Object = JObject.Parse("{number:1000, str:'string', array: [1,2,3,4,5,6]}")
A partir do Json.NET 4.0 Release 1, há suporte dinâmico nativo:
E, é claro, a melhor maneira de obter a versão atual é via NuGet.
Atualizado (11/12/2014) para tratar dos comentários:
Isso funciona perfeitamente bem. Se você inspecionar o tipo no depurador, verá que o valor é de fato dinâmico . O tipo subjacente é a
JObject
. Se você deseja controlar o tipo (como especificarExpandoObject
, faça-o).fonte
@Model.Prop
nome no Razor se o tipo de retorno for JValue.JValue
. O que me confundiu porque eu estava trabalhando na janela do depurador / janela imediata e não estava vendo apenasstring
s. David mostra isso na captura de tela inferior. AJValue
é conversível para que você pode apenas fazerstring m = jsonResponse.message
Se você apenas desserializar para dinâmico, receberá um JObject de volta. Você pode obter o que deseja usando um ExpandoObject.
fonte
Eu sei que esse post é antigo, mas o JsonConvert realmente tem um método diferente, então seria
fonte
Sim, você pode fazer isso usando o JsonConvert.DeserializeObject. Para fazer isso, basta fazer:
fonte
JsonConvert
não contém um método chamadoDeserialize
.Nota: No momento em que respondi a essa pergunta em 2010, não havia como desserializar sem algum tipo, isso permitiu que você desserializasse sem precisar definir a classe real e permitir que uma classe anônima fosse usada para fazer a desserialização.
Você precisa ter algum tipo de tipo para desserializar. Você poderia fazer algo como:
Minha resposta é baseada em uma solução para compilação do .NET 4.0 no serializador JSON. O link para desserializar para tipos anônimos está aqui:
http://blogs.msdn.com/b/alexghi/archive/2008/12/22/using-anonymous-types-to-deserialize-json-data.aspx
fonte
Se você usa o JSON.NET com a versão antiga que não JObject.
Esta é outra maneira simples de criar um objeto dinâmico a partir do JSON: https://github.com/chsword/jdynamic
Instalação do NuGet
Suporte usando o índice de string para acessar membros como:
Caso de teste
E você pode usar este utilitário da seguinte maneira:
Obtenha o valor diretamente
2.Obtenha o membro no objeto json
3.IEnumerable
De outros
fonte
Sim, é possível. Eu tenho feito isso o tempo todo.
É um pouco mais complicado para o tipo não nativo. Suponha que dentro do seu Obj, haja objetos ClassA e ClassB. Todos eles são convertidos em JObject. O que você precisa fazer é:
fonte