Domanda

Ho una classe che mantiene un riferimento a un Hashtable e serializza / deserializza quel Hashtable. Dopo la chiamata a SerializationInfo.GetValue, Hashtable non è completamente deserializzato perché la deserializzazione si verifica durante il calback IDeserialization.

Hashtable hashtable = (Hashtable) info.GetValue("hash", typeof(Hashtable));

Ho anche implementato il callback IDeserialization nella classe parent, ma anche lì Hashtable non è ancora completamente deserializzato. Mi aspettavo che fosse se la deserializzazione stava avvenendo dall'interno.

La mia domanda è: è sicuro chiamare esplicitamente Hashtable.OnDeserialization dal metodo OnDeserialization della mia classe genitore, in modo da poterlo enumerare a quel punto?

public virtual void OnDeserialization(object sender)
{
    hashtable.OnDeserialization(sender);
}
È stato utile?

Soluzione

Questo è davvero un problema interessante. Dopo aver verificato il codice di serializzazione con Reflector, penso che non ci sia generalmente una buona soluzione se una classe di riferimento utilizza IDeserializationCallback.

Probabilmente hai visto che esistono altri due modi per eseguire del codice durante la deserializzazione, gli attributi [OnDeserializing] e [OnDeserialized]. Sfortunatamente entrambi vengono eseguiti prima di IDeserializationCallback.OnDeserialization (). Questo è l'ordine di esecuzione dei metodi se si dispone di class1 che fa riferimento a class2:

Class1: [OnDeserializing]
Class2: [OnDeserializing]
Class2: [OnDeserialized]
Class1: [OnDeserialized]
Class1: IDeserializationCallback.OnDeserialization
Class2: IDeserializationCallback.OnDeserialization

Come puoi vedere, gli attributi [OnDeserializing] e [OnDeserialized] funzionano in modo coerente, ma i metodi IDeserializationCallback in realtà non ... :(

Ho anche verificato l'implementazione di OnDeserialization di Hashtable e Dictionary, ed entrambi sembrano essere sicuri per chiamare OnDeserialization più di una volta (solo la prima chiamata eseguirà l'operazione necessaria, le chiamate successive non faranno nulla).

Quindi alla fine dovresti chiamare OnDeserialization () di Hashtable, come Sean e Brian ha suggerito.

Altri suggerimenti

Sospetto che tu abbia già cercato su Google, ma mi sono imbattuto in questo modello ieri.

public BoringClass(SerializationInfo info, StreamingContext context)
{
    Hashtable hashtable = (Hashtable) info.GetValue("hash", typeof(Hashtable));
    hashtable.OnDeserialization(this);

    Console.WriteLine("Value is: " + hashtable["testItem"]);

}
Autorizzato sotto: CC-BY-SA insieme a attribuzione
Non affiliato a StackOverflow
scroll top