繁体   English   中英

从XPathNavigator.AppendChild()创建时如何设置XmlWriter.XmlWriterSettings?

[英]How to set XmlWriter.XmlWriterSettings when created from XPathNavigator.AppendChild()?

我需要将XmlWriter的XmlWriterSettings的OmitXmlDeclaration属性设置为false,以便不创建XML声明。 问题是我通过调用XPathNavigator.AppendChild()方法创建了XmlWriter。 代码如下:

    public String GetEntityXml<T>(List<T> entities)
    {
        XmlDocument xmlDoc = new XmlDocument();
        XPathNavigator nav = xmlDoc.CreateNavigator();

        using (XmlWriter writer = nav.AppendChild())
        {

            XmlSerializer ser = new XmlSerializer(typeof(List<T>), new XmlRootAttribute(typeof(T).Name + "_LIST"));
            ser.Serialize(writer, entities);
        }

        StringWriter stringWriter = new StringWriter();
        XmlTextWriter xmlTextWriter = new XmlTextWriter(stringWriter);

        xmlDoc.WriteTo(xmlTextWriter);

        string resultString = stringWriter.ToString();

        stringWriter.Close();
        xmlTextWriter.Close();

        return resultString;
    }

知道如何序列化List并且没有XML声明吗?

我在执行代码时没有收到XML声明。 序列化List<int>给了我:

<Int32_LIST xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" 
            xmlns:xsd="http://www.w3.org/2001/XMLSchema">
  <int>5</int>
  <int>7</int>
  <int>2</int>
</Int32_LIST>

请注意, OmitXmlDeclaration引用的“XML声明”通常类似于:

<?xml version="1.0" encoding="UTF-8" ?>

如果您改为引用xmlns部分,那么这些部分称为“XML 名称空间声明”,可以通过使用默认空命名空间初始化XmlSerializerNamespaces实例并将其传递给Serialize方法来消除:

XmlSerializer ser = new XmlSerializer(typeof(List<T>), new XmlRootAttribute(typeof(T).Name + "_LIST"));
var namespaces = new XmlSerializerNamespaces(new[] { new XmlQualifiedName("", "") });
ser.Serialize(writer, entities, namespaces);

以下是缩短的实现,它实现了与您的代码相同的结果:

public String GetEntityXml<T>(List<T> entities)
{
    var sb = new StringBuilder();
    var settings = new XmlWriterSettings { OmitXmlDeclaration = true };
    using (XmlWriter writer = XmlWriter.Create(sb, settings))
    {
        XmlSerializer ser = new XmlSerializer(typeof(List<T>), new XmlRootAttribute(typeof(T).Name + "_LIST"));
        var namespaces = new XmlSerializerNamespaces(new[] { new XmlQualifiedName("", "") });
        ser.Serialize(writer, entities, namespaces);
    }
    return sb.ToString();
}

尝试这种方法(切换到var以获得可读性):

public String GetEntityXml<T>(List<T> entities)
{
    var xmlDoc = new XmlDocument();
    var nav = xmlDoc.CreateNavigator();
    using (var sw = new StringWriter())
    {
        //Create an XmlWriter that will omit xml declarations
        var s = new XmlWriterSettings{ OmitXmlDeclaration = true };
        using (var xmlWriter = XmlWriter.Create(sw, s))
        {
            //Use the following to serialize without namespaces
            var ns = new XmlSerializerNamespaces();
            ns.Add("", "");
            var ser = new XmlSerializer(typeof(List<T>),
                          new XmlRootAttribute(typeof(T).Name + "_LIST"));
            ser.Serialize(xmlWriter, entities, ns);
        }

        //Pass xml string to nav.AppendChild()
        nav.AppendChild(sw.ToString());
    }

    using (var stringWriter = new StringWriter())
    {
        using (var xmlTextWriter = XmlWriter.Create(stringWriter))
        {
            xmlDoc.WriteTo(xmlTextWriter);
        }
        return stringWriter.ToString();
    }
}

您可以单独创建XmlWriter ,然后使用nav.AppendChild(string)将XML写入xmlDoc ,而不是使用nav.AppendChild()来创建XmlWriter 自己创建XmlWriter ,可以省略XML声明。 此外,在序列化时,您可能希望使用XmlSerializerNamespaces类省略xmlns:xsixmlns:xsd命名空间。

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM