Comment la désérialisation WCF instancier des objects sans appeler un constructeur?

Il y a de la magie avec la désérialisation de WCF. Comment instancie-t-il une instance du type de contrat de données sans appeler son constructeur?

Par exemple, considérons ce contrat de données:

[DataContract] public sealed class CreateMe { [DataMember] private readonly ssortingng _name; [DataMember] private readonly int _age; private readonly bool _wasConstructorCalled; public CreateMe() { _wasConstructorCalled = true; } // ... other members here } 

Lors de l’obtention d’une instance de cet object via DataContractSerializer vous verrez que le champ _wasConstructorCalled est false .

Alors, comment WCF fait-il cela? Est-ce une technique que les autres peuvent également utiliser ou est-elle cachée?

FormatterServices.GetUninitializedObject() créera une instance sans appeler un constructeur. J’ai trouvé cette classe en utilisant Reflector et en explorant certaines des principales classes de sérialisation .Net.

Je l’ai testé en utilisant l’exemple de code ci-dessous et il semble que cela fonctionne très bien:

 using System; using System.Reflection; using System.Runtime.Serialization; namespace NoConstructorThingy { class Program { static void Main() { // does not call ctor var myClass = (MyClass)FormatterServices.GetUninitializedObject(typeof(MyClass)); Console.WriteLine(myClass.One); // writes "0", constructor not called Console.WriteLine(myClass.Two); // writes "0", field initializer not called } } public class MyClass { public MyClass() { Console.WriteLine("MyClass ctor called."); One = 1; } public int One { get; private set; } public readonly int Two = 2; } } 

http://soffr.miximages.com/c%23/687556261.png

Oui, FormatterServices.GetUninitializedObject () est la source de la magie.

Si vous voulez faire une initialisation spéciale, voyez ceci. http://blogs.msdn.com/drnick/archive/2007/11/19/serialization-and-types.aspx