Ang*_*ker 5 .net c# xml performance xml-serialization
我有以下代码
public static object XmlDeserialize(string xml, Type objType)
{
StringReader stream = null;
XmlTextReader reader = null;
try
{
XmlSerializer serializer = new XmlSerializer(objType);
stream = new StringReader(xml); // Read xml data
reader = new XmlTextReader(stream); // Create reader
return serializer.Deserialize(reader);
}
finally
{
if(stream != null) stream.Close();
if(reader != null) reader.Close();
}
}
Run Code Online (Sandbox Code Playgroud)
该对象本身是通过xsd.exe生成的,看起来像这样:
/// <remarks/>
[System.CodeDom.Compiler.GeneratedCodeAttribute("xsd", "2.0.50727.3038")]
[System.SerializableAttribute()]
[System.Diagnostics.DebuggerStepThroughAttribute()]
[System.ComponentModel.DesignerCategoryAttribute("code")]
[System.Xml.Serialization.XmlTypeAttribute(AnonymousType=true)]
[System.Xml.Serialization.XmlRootAttribute(Namespace="", IsNullable=false)]
public partial class MyObject {
private DemographicsCriteriaStateStartAge[] startAgesField;
private DemographicsCriteriaStateEndAge[] endAgesField;
private DemographicsCriteriaStateFilter[] selectedFiltersField;
/// <remarks/>
[System.Xml.Serialization.XmlArrayItemAttribute("StartAge", IsNullable=false)]
public DemographicsCriteriaStateStartAge[] StartAges {
get {
return this.startAgesField;
}
set {
this.startAgesField = value;
}
}
...
Run Code Online (Sandbox Code Playgroud)
该方法通常如下所示:
var obj = (MyObject) XmlDeserialize(someXmlString, typeof(MyObject));
Run Code Online (Sandbox Code Playgroud)
以下代码行总是花费相当多的时间(与其他所有内容相比):
XmlSerializer serializer = new XmlSerializer(objType);
Run Code Online (Sandbox Code Playgroud)
这里发生了什么,例如它是否在后台编译反序列化程序集?为什么性能问题?
我该怎么做才能改善这个性能问题?
是的,它在运行时动态生成序列化程序集.您可以在Visual Studio中更改此行为.转到项目属性和构建部分."生成序列化程序集"的设置将其设置为true.这将生成一个类似于YourProject.XmlSerialiser.dll编译时的文件,并将在运行时停止此瓶颈.
但是,需要注意的一个例外是此设置仅适用于代理类型(例如,Web服务代理等).要实际强制Visual Studio 2010为常规类型生成序列化程序集,必须弄乱项目文件(.csproj)并从Sgen调用中删除/ proxytypes 或生成构建后步骤以手动调用程序集上的sgen.exe .
尝试XmlSerializer在类级别缓存每种类型的实例,这样如果使用相同的类型,您就不必每次都重新创建它:
class Foo
{
private static Dictionary<Type, XmlSerializer> xmls = new Dictionary<Type, XmlSerializer>();
// ...
public static object XmlDeserialize(string xml, Type objType)
{
StringReader stream = null;
XmlTextReader reader = null;
try
{
XmlSerializer serializer;
if(xmls.Contains(objType)) {
serializer = xmls[objType];
}
else {
serializer = new XmlSerializer(objType);
xmls[objType] = serializer;
}
stream = new StringReader(xml); // Read xml data
reader = new XmlTextReader(stream); // Create reader
return serializer.Deserialize(reader);
}
finally
{
if(stream != null) stream.Close();
if(reader != null) reader.Close();
}
}
}
Run Code Online (Sandbox Code Playgroud)