Archivio

Posts Tagged ‘serializzazione’

Serializzazione JSon e classi abstract

22 ottobre 2008 Nessun commento

Predendo spunto da un interessante post di Marco Minerva, ho provato ad implemetare il pattern Memento utilizzando appunto la serializzazione JSON. Ebbene a parte il fatto che bisogna necessariamente decorare le classi e i membri con un attributo specifico (e questo come per XmlSerializer con l’attributo Serializable è un poco bruttino e poco pi), il tutto funziona bene finché non ci sono di mezzo classi abstract. Mi spiego meglio. Una delle doti del serializzatore JSON sta nel supporto alla serializzazione delle List<T> che invece XmlSerializer non gestisce.

Bene, se T della List<T> che si vuole serializzare è una classe abstract il processo fallisce miseramente. E’ ovvio che quando vado a fare un Add sulla lista lo faccio di una classe concreta che eredita dalla classe abstract. Questo mi da il vantaggio (ovvio della programmazione ad oggetti) di avere una collezione di una “famiglia” di oggetti e non di uno dei suoi figli specifici.

Facciamo un esempio:

// classe astratta che mi rappresenta un
// generico task da eseguire
public abstract class Task
{
   private string description;
 
   public string Description
   {
     get { return this.description; }
     set { this.description = value; }
   }
}
 
// classe che mi rappresenta un bug da risolvere
public class Bug : Task
{
   // proprietà e metodi specifici.
}
 
// classe che mi rappresenta una todo da completare
public class Todo : Task
{
   // proprietà e metodi specifici.
}
 
// classe Milestone che contiene sia Todo che Bug
// creando una IList di Task posso memorizzare entrambi in un
// unica collection
public class Milestone
{
   private IList<Task> tasks = new List<Task>();
 
   public IList<Task> Tasks
   {
     get { return this.task; }
     set { this.task = value; }
   }
}

Tento la serializzazione in questo modo:

public void Test()
{
    Milestone milestone = new Milestone();
 
    Todo td1 = new Todo();
    td1.Description = "Fare e disfare";
 
    Todo td2 = new Todo();
    td2.Description = "Rifare e non disfare";
 
    milestone.Tasks.Add(td1);
    milestone.Tasks.Add(td2);
 
    string ser = Serialize(milestone);
 
    Milestone newMilestone = Deserialize(ser);
}

Dove “Serialize” e “Deserialize” sono gli stessi metodi descritti nel post di Marco. All’esecuzione del precedente codice ottengo un bel “System.Runtime.Serialization.SerializationException” in quanto probabilemente non riesce correttamente a serialize IList di Task. Vedrò di approfondire il discorso.