Open GoogleCodeExporter opened 9 years ago
Here's a sample converter that makes this much prettier:
class HashtableConverter : IConverter
{
private static readonly Type localType = typeof(Hashtable);
public void Register(IMarshalContext context)
{
context.RegisterConverter(localType, this);
context.Alias("hashtable", localType);
}
public void ToXml(object value, FieldInfo field, XmlTextWriter xml,
IMarshalContext context)
{
Hashtable ht = value as Hashtable;
Type hashtableType = ht.GetType();
context.WriteStartTag(hashtableType, field, xml);
int stackIx = context.GetStackIndex(value);
if (stackIx >= 0)
xml.WriteAttributeString("ref", stackIx.ToString());
else
{
context.Stack(ht);
foreach (object key in ht.Keys)
{
Entry hte = new Entry(key, ht[key]);
IConverter converter = context.GetConverter(hte.GetType());
if (converter == null) throw new Exception("Couldnot find converter
for: " + hte.GetType() + " having value: " + hte);
converter.ToXml(hte, null, xml, context);
}
}
context.WriteEndTag(hashtableType, field, xml);
}
public object FromXml(object parent, FieldInfo field, Type type, XmlNode xml,
IMarshalContext context)
{
Hashtable ht;
if (xml.Attributes["ref"] != null)
{
int stackIx = int.Parse(xml.Attributes["ref"].Value);
ht = context.GetStackObject(stackIx) as Hashtable;
}
else
{
int childCount = xml.ChildNodes.Count;
ht = Activator.CreateInstance(type, new object[] { childCount, 1.0f }) as
Hashtable;
// Add the object to the stack
context.Stack(ht);
foreach (XmlNode child in xml.ChildNodes)
{
Type memberType = null;
IConverter converter = context.GetConverter(child, ref memberType);
Entry hte = (Entry)converter.FromXml(null, null, memberType, child,
context);
ht.Add(hte.key, hte.value);
}
}
return ht;
}
}
public class Entry
{
public object key;
public object value;
public Entry(Object key, Object value)
{
this.key = key;
this.value = value;
}
public string toString()
{
return "key: " + key + " value: " + value;
}
}
Original comment by cgoudien...@gmail.com
on 9 Oct 2009 at 9:59
If you use he above converter, you should be able to serialize and deserialize
hashtables with ease.
If you're using the current release (1.0) of the DLL and you would like to use
this
converter without modifying the source of XStream, here is how to get it into
the
converter list:
XStream xs = new XStream();
FieldInfo f = xs.GetType().GetField("context", BindingFlags.NonPublic |
BindingFlags.Instance);
IMarshalContext mc = (IMarshalContext)f.GetValue(xs);
mc.RegisterConverter(typeof(Hashtable), new HashtableConverter());
xs.Alias("entry", typeof(Entry));
Original comment by cgoudien...@gmail.com
on 9 Oct 2009 at 10:02
Original issue reported on code.google.com by
cgoudien...@gmail.com
on 8 Oct 2009 at 7:33