Compartilhar via


Serialização JSON autônoma usando DataContractJsonSerializer

Observação

Este artigo é sobre DataContractJsonSerializer. Para a maioria dos cenários que envolvem serialização e desserialização do JSON, recomendamos as APIs no namespace System.Text.Json.

JSON (JavaScript Object Notation) é um formato de dados projetado especificamente para ser usado pelo código JavaScript em execução em páginas da Web dentro do navegador. É o formato de dados padrão usado por ASP.NET serviços AJAX criados no WCF (Windows Communication Foundation).

Esse formato também pode ser usado ao criar serviços AJAX sem integração com ASP.NET - nesse caso, XML é o padrão, mas JSON pode ser escolhido.

Por fim, se você precisar de suporte para JSON, mas não estiver criando um serviço AJAX, DataContractJsonSerializer possibilita serializar diretamente objetos .NET em dados JSON e desserializar esses dados de volta em instâncias de tipos .NET. Para obter uma descrição de como fazer isso, consulte Como serializar e desserializar dados JSON.

Ao trabalhar com JSON, há suporte para os mesmos tipos de .NET, com algumas exceções, conforme são compatíveis com o DataContractSerializer. Para obter uma lista dos tipos com suporte, consulte Tipos compatíveis com o Serializador de Contrato de Dados. Isso inclui a maioria dos tipos primitivos, a maioria dos tipos de matriz e coleção, bem como tipos complexos que usam o DataContractAttribute e DataMemberAttribute.

Mapear tipos .NET para tipos JSON

A tabela a seguir mostra a correspondência entre tipos .NET e tipos JSON/JavaScript quando mapeada por procedimentos de serialização e desserialização.

Tipos de .NET JSON/JavaScript Anotações
Todos os tipos numéricos, por exemplo Int32, Decimal ou Double Número Valores especiais, como Double.NaN, Double.PositiveInfinity e Double.NegativeInfinity não têm suporte e resultam em JSON inválido.
Enum Número Consulte "Enumerações e JSON" mais adiante neste artigo.
Boolean Booliano
String, Char fio
TimeSpan Guid Uri fio O formato desses tipos em JSON é o mesmo que em XML (essencialmente, intervalo de tempo no formato de duração ISO 8601, GUID no formato "12345678-ABCD-ABCD-ABCD-1234567890AB" e URI em sua forma de cadeia de caracteres natural como "http://www.example.com"). Para obter informações precisas, consulte Referência de esquema de contrato de dados.
XmlQualifiedName fio O formato é "name:namespace" (qualquer coisa antes dos primeiros dois-pontos é o nome). O nome ou o namespace podem estar ausentes. Se não houver namespace, os dois-pontos também poderão ser omitidos.
Command do tipo System.Windows.Input.ICommand Matriz de números Cada número representa o valor de um byte.
DateTime DateTime ou Cadeia de Caracteres Consulte Datas/Horas e JSON mais adiante neste artigo.
DateTimeOffset Tipo complexo Consulte Datas/Horas e JSON mais adiante neste artigo.
Tipos de XML e ADO.NET (XmlElement,

XElement. Matrizes de XmlNode,

ISerializable,

DataSet).
fio Consulte a seção XML Types e JSON deste artigo.
DBNull Tipo complexo vazio --
Coleções, dicionários e matrizes Matriz Consulte a seção Coleções, Dicionários e Matrizes deste tópico.
Tipos complexos (com o DataContractAttribute ou SerializableAttribute aplicado) Tipo complexo Os membros de dados tornam-se membros do tipo complexo JavaScript.
Tipos complexos que implementam a ISerializable interface) Tipo complexo O mesmo que outros tipos complexos, mas alguns ISerializable tipos não são compatíveis – consulte Suporte ISerializable.
valor Null para qualquer tipo Nulo Tipos de valor anuláveis também têm suporte e são mapeados para JSON da mesma forma que tipos de valor não anuláveis.

Enumerações e JSON

Os valores de membro de enumeração são tratados como números em JSON, que é diferente de como eles são tratados em contratos de dados, em que são incluídos como nomes de membro. Para obter mais informações sobre o tratamento do contrato de dados, consulte Tipos de Enumeração em Contratos de Dados.

  • Por exemplo, se você tiver public enum Color {red, green, blue, yellow, pink}, serializar yellow produzirá o número 3 e não a cadeia de caracteres "amarela".

  • Todos os enum membros são serializáveis. Os EnumMemberAttribute atributos e os NonSerializedAttribute atributos serão ignorados se usados.

  • É possível desserializar um valor inexistente enum – por exemplo, o valor 87 pode ser desserializado na enumeração Color anterior, embora não haja nenhum nome de cor correspondente definido.

  • Um sinalizador enum não é especial e é tratado da mesma forma que qualquer outro enum.

Datas/horas e JSON

O formato JSON não dá suporte diretamente a datas e horas. No entanto, eles são muito comumente usados e ASP.NET AJAX fornece suporte especial para esses tipos. Ao usar ASP.NET proxies AJAX, o DateTime tipo no .NET corresponde totalmente ao DateTime tipo em JavaScript.

  • Quando não estiver usando ASP.NET, um DateTime tipo é representado em JSON como uma cadeia de caracteres com um formato especial descrito na seção Informações Avançadas deste tópico.

  • DateTimeOffset é representado no JSON como um tipo complexo: {"DateTime":d ateTime",OffsetMinutes":offsetMinutes}. O membro offsetMinutes é o deslocamento de hora local do Tempo Médio de Greenwich (GMT), também conhecido como Tempo Universal Coordenado (UTC), associado ao local do evento de interesse. O membro dateTime representa a instância no tempo em que o evento de interesse ocorreu (novamente, ele se torna um DateTime em JavaScript quando ASP.NET AJAX está em uso, e uma cadeia de caracteres quando não está). Na serialização, o membro dateTime é sempre serializado em GMT. Portanto, se estiver descrevendo 3h de Nova York, dateTime terá um componente de tempo de 8h e offsetMinutes será 300 (menos 300 minutos ou 5 horas de GMT).

    Observação

    DateTime e DateTimeOffset objetos, quando serializados para JSON, preservam apenas as informações para precisão de milissegundos. Valores abaixo de milissegundos (micro/nanossegundos) são perdidos durante a serialização.

Tipos XML e JSON

Os tipos XML tornam-se cadeias de caracteres JSON.

  • Por exemplo, se um membro de dados "q" do tipo XElement contiver <abc/>, o JSON será {"q":"<abc/>"}.

  • Há algumas regras especiais que especificam como o XML é encapsulado – para obter mais informações, consulte a seção Informações Avançadas mais adiante neste artigo.

  • Se você estiver usando ASP.NET AJAX e não quiser usar strings no JavaScript, mas preferir usar o DOM XML, defina a propriedade ResponseFormat como XML no WebGetAttribute ou a propriedade ResponseFormat como XML no WebInvokeAttribute.

Coleções, dicionários e matrizes

Todas as coleções, dicionários e matrizes são representadas em JSON como matrizes.

  • Qualquer personalização que use a CollectionDataContractAttribute é ignorada na representação JSON.

  • Dicionários não são uma maneira de trabalhar diretamente com JSON. O dicionário <string.object> pode não ser compatível da mesma forma que o WCF, conforme o esperado, de trabalhar com outras tecnologias JSON. Por exemplo, se "abc" for mapeado para "xyz" e "def" for mapeado para 42 em um dicionário, a representação JSON não será {"abc":"xyz","def":42} mas será [{"Key":"abc","Value":"xyz"},{"Key":"def","Value":42}] em vez disso.

  • Se você quiser trabalhar diretamente com JSON (acessando chaves e valores dinamicamente, sem definir previamente um contrato rígido), você terá várias opções:

    • Considere usar o exemplo de Serialização JSON de tipagem fraca (AJAX).

    • Considere usar os ISerializable construtores de interface e desserialização – esses dois mecanismos permitem que você acesse pares de chave/valor JSON na serialização e desserialização, respectivamente, mas não funcionam em cenários parciais de confiança.

    • Considere trabalhar com o mapeamento entre JSON e XML em vez de usar um serializador.

    • O polimorfismo no contexto da serialização refere-se à capacidade de serializar um tipo derivado em que seu tipo base é esperado. Há regras especiais específicas de JSON ao usar coleções polimorficamente, quando, por exemplo, atribuir uma coleção a uma Object. Esse problema é mais discutido na seção Informações Avançadas mais adiante neste artigo.

Detalhes adicionais

Ordem dos membros de dados

A ordem dos membros de dados não é importante ao usar JSON. Especificamente, mesmo se Order estiver definido, os dados JSON ainda poderão ser desserializados em qualquer ordem.

Tipos JSON

O tipo JSON não precisa corresponder à tabela anterior sobre desserialização. Por exemplo, um Int normalmente é mapeado para um número JSON, mas também pode ser desserializado com êxito de uma cadeia de caracteres JSON, desde que essa cadeia de caracteres contenha um número válido. Ou seja, {"q":42} e {"q":"42"} são válidos se houver um Int membro de dados chamado "q".

Polimorfismo

A serialização polimórfica consiste na capacidade de serializar um tipo derivado em que seu tipo base é esperado. A serialização JSON é suportada pelo WCF de forma comparável à maneira como é suportada a serialização XML. Por exemplo, você pode serializar MyDerivedType onde MyBaseType é esperado ou serializar Int onde Object é esperado.

As informações de tipo podem ser perdidas ao desserializar um tipo derivado se o tipo base for esperado, a menos que você esteja desserializando um tipo complexo. Por exemplo, se Uri for serializado onde Object é esperado, isso resultará em uma cadeia de caracteres JSON. Se essa cadeia de caracteres for desserializada novamente em Object, será retornado um .NET String. O desserializador não sabe que a cadeia de caracteres foi inicialmente do tipo Uri. Geralmente, ao esperar Object, todas as cadeias de caracteres JSON são desserializadas como cadeias de caracteres .NET e todas as matrizes JSON usadas para serializar coleções, dicionários e matrizes do .NET são desserializadas como .NET Array do tipo Object, independentemente do tipo original real. Um JSON booliano é mapeado para um .NET Boolean. No entanto, ao esperar um Object, os números JSON são desserializados como .NET Int32, Decimal ou Double, onde o tipo mais apropriado é escolhido automaticamente.

Ao desserializar para um tipo de interface, o DataContractJsonSerializer é desserializado como se o tipo declarado fosse um objeto.

Ao trabalhar com sua própria base e tipos derivados, usar o KnownTypeAttribute, ServiceKnownTypeAttribute ou um mecanismo equivalente normalmente é necessário. Por exemplo, se você tiver uma operação que tenha um valor retornado Animal e ela realmente retornar uma instância de Cat (derivada de Animal), você deverá aplicar o KnownTypeAttribute, ao tipo Animal ou o ServiceKnownTypeAttribute à operação e especificar o tipo Cat nesses atributos. Para obter mais informações, consulte Tipos conhecidos do contrato de dados.

Para obter detalhes de como funciona a serialização polimórfica e uma discussão sobre algumas das limitações que devem ser respeitadas ao usá-la, consulte a seção Informações Avançadas mais adiante neste artigo.

Controle de versão

Os recursos de controle de versão do contrato de dados, incluindo a IExtensibleDataObject interface, têm suporte total no JSON. Além disso, na maioria dos casos, é possível desserializar um tipo em um formato (por exemplo, XML) e serializá-lo em outro formato (por exemplo, JSON) e ainda preservar os dados em IExtensibleDataObject. Para obter mais informações, consulte Forward-Compatible Data Contracts. Lembre-se de que JSON é inerentemente sem ordem, portanto qualquer informação sobre a ordenação é perdida. Além disso, o JSON não dá suporte a vários pares chave/valor com o mesmo nome de chave. Por fim, todas as operações em IExtensibleDataObject são inerentemente polimórficas - ou seja, os seus tipos derivados são atribuídos a Object, o tipo base para todos os tipos.

JSON em URLs

Ao usar endpoints AJAX do ASP.NET com o método HTTP GET (usando o atributo WebGetAttribute), os parâmetros de entrada aparecem na URL da solicitação em vez do corpo da requisição. Há suporte para JSON mesmo na URL de solicitação, portanto, se você tiver uma operação que usa um Int chamado "número" e um Person tipo complexo chamado "p", a URL poderá ser semelhante à URL a seguir.

http://example.com/myservice.svc/MyOperation?number=7&p={"name":"John","age":42}

Se você estiver usando um controle e um proxy do AJAX Script Manager ASP.NET para chamar o serviço, essa URL será gerada automaticamente pelo proxy e não será vista. O JSON não pode ser usado em URLs em endpoints AJAX que não são do ASP.NET.

Informações avançadas

Suporte ISerializable

Tipos ISerializable com suporte e sem suporte

Em geral, os tipos que implementam a ISerializable interface têm suporte total ao serializar/desserializar o JSON. No entanto, alguns desses tipos (incluindo alguns tipos do .NET Framework) são implementados de maneira que os aspectos específicos de serialização do JSON impedem que eles sejam desserializados corretamente.

  • Com ISerializable, o tipo de membros de dados individuais nunca é conhecido com antecedência. Isso leva a uma situação polimórfica semelhante à desserialização de tipos em um objeto. Conforme mencionado antes, isso pode levar à perda de informações de tipo no JSON. Por exemplo, um tipo que serializa um enum em sua implementação ISerializable e tenta desserializar novamente diretamente em um enum (sem conversões adequadas) falha, pois um enum é serializado usando números em JSON e números JSON desserializam em tipos numéricos .NET internos (Int32, Decimal ou Double). Portanto, o fato de que o número usado para ser um valor enum é perdido.

  • Um ISerializable tipo que depende de uma determinada ordem de desserialização em seu construtor de desserialização também pode falhar em desserializar alguns dados JSON, pois a maioria dos serializadores JSON não garante nenhuma ordem específica.

Tipos de fábrica

Embora a IObjectReference interface seja geralmente suportada no JSON, quaisquer tipos que requerem o recurso "tipo de fábrica" (retornando uma instância de um tipo diferente do tipo GetRealObject(StreamingContext) que implementa a interface) não são suportados.

Formato datetime wire

DateTime os valores aparecem como cadeias de caracteres JSON na forma de "/Date(700000+0500)/", em que o primeiro número (700000 no exemplo fornecido) é o número de milissegundos no fuso horário GMT, horário regular (sem horário de verão) desde meia-noite de 1º de janeiro de 1970. O número pode ser negativo para representar horários anteriores. A parte que consiste em "+0500" no exemplo é opcional e indica que a hora é do tipo Local, ou seja, deve ser convertida para o fuso horário local durante a desserialização. Se estiver ausente, o tempo será desserializado como Utc. O número real ("0500" neste exemplo) e seu sinal (+ ou -) são ignorados.

Ao serializar DateTime, Local e Unspecified, as horas são gravadas com um deslocamento e Utc é gravado sem.

O código JavaScript do cliente ASP.NET AJAX converte automaticamente essas cadeias de caracteres em instâncias javaScript DateTime . Se houver outras cadeias de caracteres que tenham uma forma semelhante que não sejam do tipo DateTime no .NET, elas também serão convertidas.

A conversão só ocorrerá se os caracteres "/" forem escapados (ou seja, o JSON se parecerá com "\/Date(700000+0500)\/"), e, por esse motivo, o codificador JSON do WCF (habilitado pelo WebHttpBinding) sempre escapará do caractere "/".

XML em cadeias de caracteres JSON

XmlElement

XmlElement é serializado como está, sem encapsulamento. Por exemplo, o membro de dados "x" do tipo XmlElement que contém <abc/> é representado da seguinte maneira:

{"x":"<abc/>"}

Matrizes de XmlNode

Array os objetos do tipo XmlNode são encapsulados em um elemento chamado ArrayOfXmlNode no namespace de contrato de dados padrão para o tipo. Se "x" for uma matriz que contém o nó de atributo "N" no namespace "ns" que contém "valor" e um nó de elemento vazio "M", a representação será a seguinte.

{"x":"<ArrayOfXmlNode xmlns=\"http://schemas.datacontract.org/2004/07/System.Xml\" a:N=\"value\" xmlns:a=\"ns\"><M/></ArrayOfXmlNode>"}

Os atributos no namespace vazio no início das matrizes XmlNode (antes de outros elementos) não têm suporte.

Tipos IXmlSerializable, incluindo XElement e DataSet

ISerializable tipos subdividem em "tipos de conteúdo", "tipos de conjunto de dados" e "tipos de elemento". Para obter definições desses tipos, consulte XML e tipos de ADO.NET em contratos de dados.

Os tipos "Content" e "DataSet" são serializados de maneira semelhante aos Array objetos de XmlNode discutidos na seção anterior. Eles são encapsulados em um elemento cujo nome e namespace correspondem ao nome do contrato de dados e ao namespace do tipo em questão.

Tipos de "elemento", como XElement são serializados como estão, semelhantes aos XmlElement discutidos anteriormente neste artigo.

Polimorfismo

Preservando informações de tipo

Conforme indicado anteriormente, o polimorfismo é suportado no JSON com algumas limitações. O JavaScript é uma linguagem de tipagem fraca e a identificação de tipos normalmente não é um problema. No entanto, ao usar JSON para se comunicar entre um sistema de tipo forte (.NET) e um sistema de tipo fraco (JavaScript), é útil preservar a identidade do tipo. Por exemplo, tipos cujos nomes de contrato de dados são "Square" e "Circle" são derivados de um tipo cujo nome de contrato de dados é "Shape". Se "Circle" for enviado do .NET para JavaScript e mais tarde for retornado para um método .NET que espera "Shape", será útil para o lado do .NET saber que o objeto em questão era originalmente um "Círculo" – caso contrário, qualquer informação específica ao tipo derivado (por exemplo, membro de dados "radius" em "Circle") pode ser perdida.

Para preservar a identidade do tipo, ao serializar tipos complexos para JSON, uma "dica de tipo" pode ser adicionada e o desserializador reconhece a dica e age adequadamente. A "dica de tipo" é um par de chave/valor JSON com o nome da chave "__type" (dois sublinhados seguidos pela palavra "type"). O valor é uma cadeia de caracteres JSON do formulário "DataContractName:DataContractNamespace" (qualquer coisa até os primeiros dois-pontos é o nome). Usando o exemplo anterior, "Círculo" pode ser serializado da seguinte maneira.

{"__type":"Circle:http://example.com/myNamespace","x":50,"y":70,"radius":10}

A indicação de tipo é muito semelhante ao atributo xsi:type definido pelo padrão XML Schema Instance e usado ao serializar/desserializar XML.

Os membros de dados chamados "__type" são proibidos devido a um possível conflito com a dica de tipo.

Reduzindo o tamanho das dicas de tipo

Para reduzir o tamanho das mensagens JSON, o prefixo de namespace do contrato de dados padrão (http://schemas.datacontract.org/2004/07/) é substituído pelo caractere "#". (Para tornar essa substituição reversível, uma regra de escape é usada: se o namespace começar com os caracteres "#" ou "\", eles serão acrescentados com um caractere "\" extra). Portanto, se "Circle" for um tipo no namespace do .NET "MyApp.Shapes", seu namespace de contrato de dados padrão será http://schemas.datacontract.org/2004/07/MyApp. As formas e a representação JSON são as seguintes.

{"__type":"Circle:#MyApp.Shapes","x":50,"y":70,"radius":10}

Os nomes truncados (#MyApp.Shapes) e completos (http://schemas.datacontract.org/2004/07/MyApp.Shapes) são compreendidos na desserialização.

Posição da dica de tipo em objetos JSON

Observe que a dica de tipo deve aparecer primeiro na representação JSON. Esse é o único caso em que a ordem dos pares chave/valor é importante no processamento JSON. Por exemplo, o seguinte não é uma maneira válida de especificar a indicação de tipo.

{"x":50,"y":70,"radius":10,"__type":"Circle:#MyApp.Shapes"}

DataContractJsonSerializer usado pelo WCF e pelas páginas de cliente ASP.NET AJAX sempre emitem a dica de tipo primeiro.

Dicas de tipo se aplicam somente a tipos complexos

Não há como emitir uma dica de tipo para tipos não complexos. Por exemplo, se uma operação tiver um Object tipo de retorno, mas retornar um Círculo, a representação JSON poderá ser conforme mostrado anteriormente e as informações de tipo serão preservadas. No entanto, se Uri for retornado, a representação JSON será uma cadeia de caracteres e o fato de que a cadeia de caracteres usada para representar um Uri será perdida. Isso se aplica não apenas a tipos primitivos, mas também a coleções e matrizes.

Quando as dicas de tipo são emitidas

As indicações de tipo podem aumentar significativamente o tamanho da mensagem (uma maneira de mitigar isso é usar namespaces de contrato de dados mais curtos, se possível). Portanto, as seguintes regras regem se as dicas de tipo forem emitidas:

  • Ao usar ASP.NET AJAX, as dicas de tipo sempre são emitidas sempre que possível, mesmo que não haja nenhuma atribuição base/derivada, por exemplo, mesmo que um Circle seja atribuído a um Circle. Isso é necessário para habilitar completamente o processo de chamada do ambiente JSON de tipagem fraca para o ambiente .NET de tipagem forte, garantindo que não haja perda inesperada de informações.

  • Ao usar serviços AJAX sem integração ASP.NET, as dicas de tipo só são emitidas quando há uma atribuição base/derivada, ou seja, emitida quando Circle é atribuído a Shape ou Object, mas não quando atribuído a Circle. Isso fornece as informações mínimas necessárias para implementar corretamente um cliente JavaScript, melhorando o desempenho, mas não protege contra perda de informações de tipo em clientes projetados incorretamente. Evite atribuições base/derivadas completamente no servidor se quiser evitar lidar com esse problema no cliente.

  • Ao usar o DataContractSerializer tipo, o alwaysEmitTypeInformation parâmetro de construtor permite que você escolha entre os dois modos anteriores, com o padrão sendo "false" (apenas emitir dicas de tipo quando necessário).

Nomes de membros de dados duplicados

Informações de tipo derivadas estão presentes no mesmo objeto JSON junto com informações de tipo base e podem ocorrer em qualquer ordem. Por exemplo, Shape pode ser representado da seguinte maneira.

{"__type":"Shape:#MyApp.Shapes","x":50,"y":70}

Considerando que o Círculo pode ser representado da seguinte maneira.

{"__type":"Circle:#MyApp.Shapes","x":50, "radius":10,"y":70}

Se o tipo base Shape também contivesse um membro de dados chamado "radius", isso levaria a uma colisão tanto na serialização (porque os objetos JSON não podem ter nomes de chave repetidos) quanto na desserialização (porque não está claro se "radius" se refere a Shape.radius ou Circle.radius). Portanto, embora o conceito de "ocultação de propriedade" (membros de dados com o mesmo nome em classes baseadas e derivadas) geralmente não seja recomendado em classes de contrato de dados, ele é realmente proibido no caso de JSON.

Tipos polimorfismo e IXmlSerializable

IXmlSerializable os tipos podem ser atribuídos polimorficamente uns aos outros, desde que os requisitos de Tipos Conhecidos sejam atendidos, de acordo com as regras habituais de contrato de dados. No entanto, serializar um IXmlSerializable tipo no lugar de Object resulta na perda de informações de tipo, pois o resultado é uma cadeia de caracteres JSON.

Polimorfismo e determinados tipos de interface

É proibido serializar um tipo de coleção ou um tipo que implementa IXmlSerializable, onde um tipo de não coleção, que não seja IXmlSerializable (exceto para Object), é esperado. Por exemplo, uma interface personalizada chamada IMyInterface e um tipo MyType que implementam tanto IEnumerable<T> do tipo int quanto IMyInterface. É proibido retornar MyType de uma operação cujo tipo de retorno é IMyInterface. Isso ocorre porque MyType deve ser serializado como um array JSON e requer uma dica de tipo. Como já foi mencionado, não é possível incluir uma dica de tipo em arrays, apenas em tipos complexos.

Tipos e configuração conhecidos

Todos os mecanismos de Tipo Conhecido usados pelo DataContractSerializer também têm suporte da mesma forma pelo DataContractJsonSerializer. Ambos os serializadores leem o mesmo elemento de configuração, <dataContractSerializer> em <system.runtime.serialization>, para descobrir tipos conhecidos adicionados por meio de um arquivo de configuração.

Coleções atribuídas ao objeto

As coleções atribuídas ao Objeto são serializadas como se fossem coleções que implementam IEnumerable<T>: uma matriz JSON com cada entrada que tem uma dica de tipo se for um tipo complexo. Por exemplo, um List<T> do tipo Shape atribuído a Object se parece com o seguinte.

[{"__type":"Shape:#MyApp.Shapes","x":50,"y":70},
{"__type":"Shape:#MyApp.Shapes","x":58,"y":73},
{"__type":"Shape:#MyApp.Shapes","x":41,"y":32}]

Quando desserializado novamente em Object:

  • Shape deve estar na lista Tipos Conhecidos. Ter List<T> de tipo Shape em tipos conhecidos não tem efeito. Observe que você não precisa adicionar Shape a tipos conhecidos sobre serialização nesse caso – isso é feito automaticamente.

  • A coleção é desserializada como um Array de tipo Object que contém Shape instâncias.

Coleções derivadas atribuídas a coleções base

Quando uma coleção derivada é atribuída a uma coleção base, a coleção geralmente é serializada como se fosse uma coleção do tipo base. No entanto, se o tipo de item da coleção derivada não puder ser atribuído ao tipo de item da coleção base, uma exceção será gerada.

Dicas de tipo e dicionários

Quando um dicionário é atribuído a um Object, cada entrada de Chave e Valor no dicionário é tratada como se tivesse sido atribuída a Object e recebe uma dica de tipo.

Ao serializar tipos de dicionário, o objeto JSON que contém os membros "Key" e "Value" não é afetado pela alwaysEmitTypeInformation configuração e contém apenas uma dica de tipo quando as regras de coleção anteriores exigem isso.

Nomes de chave JSON válidos

O serializador codifica nomes de chave que não são nomes XML válidos. Por exemplo, um membro de dados com o nome "123" teria um nome codificado como "_x0031__x0032__x0033_" porque "123" é um nome de elemento XML inválido (começa com um dígito). Uma situação semelhante pode surgir com alguns conjuntos de caracteres internacionais não válidos em nomes XML. Para obter uma explicação desse efeito de XML no processamento JSON, consulte Mapeamento entre JSON e XML.

Consulte também