slugster,
Vous pouvez envisager de passer à la place XMLSerializer. Voici ce que j'ai déterminé avec le temps:
Les classes XMLSerializer et DataContractSerializer fournissent un moyen simple de sérialiser et de désérialiser les graphes d'objets vers et à partir de XML.
Les principales différences sont les suivantes: 1.
XMLSerializer a charge beaucoup plus petite que DCS si vous utilisez [XmlAttribute] au lieu de [XmlElement]
DCS stocker toujours des valeurs comme éléments
2.
DCS est " opt-in "plutôt que" opt-out "
Avec DCS vous marquez explicitement ce que vous voulez sérialiser avec [DataMember]
Avec DCS vous pouvez sérialiser n'importe quel champ ou propriété, même s'ils sont marqués protégés ou privés
Avec DCS vous pouvez utiliser [IgnoreDataMember] pour avoir le sérialiseur ignorer certaines propriétés
Avec des propriétés publiques XMLSerializer sont sérialisés, et ont besoin d'être setters désérialisée
Avec XmlSerializer, vous pouvez utiliser [XmlIgnore] pour que le sérialiseur ignorer les propriétés publiques
3.
CONNAÎTRE! DCS.ReadObject ne remet pas les constructeurs lors de la désérialisation
Si vous devez effectuer l'initialisation, DCS prend en charge les crochets de rappel suivants:
[OnDeserializing], [OnDeserialized], [OnSerializing], [OnSerialized]
(également utile pour gérer les problèmes de versioning)
Si vous voulez avoir la possibilité de basculer entre les deux serializers, vous pouvez utiliser les deux ensembles d'attributs simultanément, comme dans:
[DataContract]
[XmlRoot]
public class ProfilePerson : NotifyPropertyChanges
{
[XmlAttribute]
[DataMember]
public string FirstName { get { return m_FirstName; } set { SetProperty(ref m_FirstName, value); } }
private string m_FirstName;
[XmlElement]
[DataMember]
public PersonLocation Location { get { return m_Location; } set { SetProperty(ref m_Location, value); } }
private PersonLocation m_Location = new PersonLocation(); // Should change over time
[XmlIgnore]
[IgnoreDataMember]
public Profile ParentProfile { get { return m_ParentProfile; } set { SetProperty(ref m_ParentProfile, value); } }
private Profile m_ParentProfile = null;
public ProfilePerson()
{
}
}
aussi, consultez ma classe sérialiseur qui peut basculer entre les deux:
using System;
using System.IO;
using System.Runtime.Serialization;
using System.Text;
using System.Xml;
using System.Xml.Serialization;
namespace ClassLibrary
{
// Instantiate this class to serialize objects using either XmlSerializer or DataContractSerializer
internal class Serializer
{
private readonly bool m_bDCS;
internal Serializer(bool bDCS)
{
m_bDCS = bDCS;
}
internal TT Deserialize<TT>(string input)
{
MemoryStream stream = new MemoryStream(input.ToByteArray());
if (m_bDCS)
{
DataContractSerializer dc = new DataContractSerializer(typeof(TT));
return (TT)dc.ReadObject(stream);
}
else
{
XmlSerializer xs = new XmlSerializer(typeof(TT));
return (TT)xs.Deserialize(stream);
}
}
internal string Serialize<TT>(object obj)
{
MemoryStream stream = new MemoryStream();
if (m_bDCS)
{
DataContractSerializer dc = new DataContractSerializer(typeof(TT));
dc.WriteObject(stream, obj);
}
else
{
XmlSerializer xs = new XmlSerializer(typeof(TT));
xs.Serialize(stream, obj);
}
// be aware that the Unicode Byte-Order Mark will be at the front of the string
return stream.ToArray().ToUtfString();
}
internal string SerializeToString<TT>(object obj)
{
StringBuilder builder = new StringBuilder();
XmlWriter xmlWriter = XmlWriter.Create(builder);
if (m_bDCS)
{
DataContractSerializer dc = new DataContractSerializer(typeof(TT));
dc.WriteObject(xmlWriter, obj);
}
else
{
XmlSerializer xs = new XmlSerializer(typeof(TT));
xs.Serialize(xmlWriter, obj);
}
string xml = builder.ToString();
xml = RegexHelper.ReplacePattern(xml, RegexHelper.WildcardToPattern("<?xml*>", WildcardSearch.Anywhere), string.Empty);
xml = RegexHelper.ReplacePattern(xml, RegexHelper.WildcardToPattern(" xmlns:*\"*\"", WildcardSearch.Anywhere), string.Empty);
xml = xml.Replace(Environment.NewLine + " ", string.Empty);
xml = xml.Replace(Environment.NewLine, string.Empty);
return xml;
}
}
}
Bonne chance, Jim
McCurdy
Face To Face Software et YinYangMoney
Merci Jim, bonne réponse. Malheureusement, je ne peux pas utiliser XmlSerializer en raison de problèmes d'espace de noms et d'objets identiques, d'où mon utilisation du DCS. Et le point # 3 sur le DCS était aussi bon, je suis sûr qu'il a attrapé quelques personnes dans le passé :) – slugster
Jim, je sais que l'optimisation prématurée est la racine du plus mauvais, mais 'nouveau DataContractSerializer (typeof (TT)) 'et' new XmlSerializer (typeof (TT)) 'sont des opérations * très * coûteuses. Vous pouvez les mettre en cache dans un 'Dictionnaire statique' etc si vous avez trouvé que ce code devenait lent. –
Rob, Bonne observation sur la performance. Je vais apporter vos modifications suggérées dans mes applications. Merci ... –