如何创建忽略命名空间且不检查字符的 XmlTextReader

Jeh*_*hof 2 c# xml

我想使用一个XmlTextReader忽略命名空间并且不检查字符的。要忽略命名空间,我可以设置属性Namespaces=false而不检查字符,我可以使用XmlReaderSettings.CheckCharacters = false.

我尝试创建XmlTextReaderusing it 构造函数,但这不允许我传入配置的XmlReaderSettings. 该属性Settings是只读的,因此我无法在构建后设置它。

XmlTextReader reader = new XmlTextReader(gzs) { Namespaces = false};
reader.Settings = new XmlReaderSettings { CheckCharacters = false}; // readonly
Run Code Online (Sandbox Code Playgroud)

使用Create()基类的静态方法,XmlReader我可以传入XmlReaderSettings,但该方法返回 aXmlTextReaderImpl并且没有Namespace要设置的属性,并且不能强制转换为XmlTextReader

var settings = new XmlReaderSettings { CheckCharacters = false}; 
var reader = XmlTextReader.Create(gzs, settings); 
XmlTextReader textReader = reader as XmlTextReader  // not possible
Run Code Online (Sandbox Code Playgroud)

那么如何创建这样的 XmlTextReader 呢?甚至有可能吗?是否有任何属性XmlReaderSettings可以忽略命名空间?

Alt*_*ant 5

这并不难。

我的任务是反序列化具有或不具有默认命名空间声明的相同结构的 xml 文件。

首先,我在 XmlTextReader 解决方案中找到了这个讨论:NamespaceIgnorantXmlTextReader。但是 MSDN 建议不要使用 XmlTextReader,而是使用 XmlReader。

所以我们需要在 XmlReader 上做同样的事情。

XmlReader 是一个抽象类,我们需要先做一个包装器。是一篇很好的文章如何做到这一点。而这里是一个现成XmlWrappingReader。

然后我们需要扩展它:

public class XmlExtendableReader : XmlWrappingReader
{
    private bool _ignoreNamespace { get; set; }

    public XmlExtendableReader(TextReader input, XmlReaderSettings settings, bool ignoreNamespace = false)
    : base(XmlReader.Create(input, settings))
    {
        _ignoreNamespace = ignoreNamespace;
    }

    public override string NamespaceURI
    {
        get
        {
            return _ignoreNamespace ? String.Empty : base.NamespaceURI;
        }
    }
}
Run Code Online (Sandbox Code Playgroud)

就是这样。现在我们可以使用它并控制 XmlReaderSettings 和命名空间处理:

XmlReaderSettings settings = new XmlReaderSettings()
{
    CheckCharacters = false,
    ConformanceLevel = ConformanceLevel.Document,
    DtdProcessing = DtdProcessing.Ignore,
    IgnoreComments = true,
    IgnoreProcessingInstructions = true,
    IgnoreWhitespace = true,
    ValidationType = ValidationType.None
};

using (XmlExtendableReader xmlreader = new XmlExtendableReader(reader, settings, true))
    _entities = ((Orders)_serializer.Deserialize(xmlreader)).Order;
Run Code Online (Sandbox Code Playgroud)