首页
学习
活动
专区
圈层
工具
发布
首页
学习
活动
专区
圈层
工具
MCP广场
社区首页 >问答首页 >XmlReader ReadStartElement引起XmlException

XmlReader ReadStartElement引起XmlException
EN

Stack Overflow用户
提问于 2011-02-13 03:27:09
回答 1查看 10K关注 0票数 6

我正在使用Silverlight项目中的XmlReader编写文件阅读器。然而,我得到了一些错误(特别是关于XmlReader.ReadStartElement方法),这使我相信我误解了如何使用它。

基本上,下面是我正在使用的Xml格式的示例:

代码语言:javascript
运行
复制
<?xml version="1.0" encoding="utf-8" standalone="no"?>
<root>
    <EmptyElement />
    <NonEmptyElement Name="NonEmptyElement">
        <SubElement Name="SubElement" />
    </NonEmptyElement>
</root>

下面是一些代码的示例,其使用方式与我使用它的方式相同:

代码语言:javascript
运行
复制
public void ReadData(XmlReader reader)
{
    // Move to root element
    reader.ReadStartElement("root");

    // Move to the empty element
    reader.ReadStartElement("EmptyElement");

    // Read any children
    while(reader.ReadToNextSibling("SubEmptyElement"))
    {
        // ...
    }

    // Read the end of the empty element
    reader.ReadEndElement();

    // Move to the non empty element
    reader.ReadStartElement("NonEmptyElement");    // NOTE: This is where I get the error.

    // ...
}

所以,基本上,我只是试着读每一个元素和任何包含的孩子。我在高亮显示的点上得到的错误如下:

错误描述

Xml_InvalidNodeType参数: None,10,8调试资源字符串不可用。通常,键和参数提供足够的信息来诊断问题。请参阅http://go.microsoft.com/fwlink/?linkid=106663&Version=4.0.51204.0&File=System.Xml.dll&Key=Xml_InvalidNodeType

错误堆栈跟踪

at System.Xml.XmlReader.ReadStartElement(字符串名称) at

如对此有任何建议或指导,将不胜感激。

由于这个阅读器需要相当通用的编辑,所以可以假定EmptyElement可能包含EmptyElement的子元素。因此,读取任何SubEmptyElements的尝试都应该是有效的。

EN

回答 1

Stack Overflow用户

回答已采纳

发布于 2011-02-13 03:52:10

<SubElement/>不是<EmptyElement>的兄弟,所以<NonEmptyElement>将被完全跳过,您对ReadEndElement()的调用将读取end元素</root>。当您随后尝试读取"NonEmptyElement“时,将没有剩下的元素,您将得到一个XmlException:{”None“是一个无效的XmlNodeType。

还请注意,由于<EmptyElement/>是空的,所以当您使用ReadStartElement("EmptyElement")时,您将读取整个元素,并且不需要使用ReadEndElement()。

我还建议您将您的读取器设置配置为IgnoreWhitespace (如果您还没有这样做的话),以避免在没有预期时读取(不重要)空白文本节点带来的任何复杂情况。

尝试将NonEmptyElement的读物向上移动:

代码语言:javascript
运行
复制
public static void ReadData(XmlReader reader)
{
    reader.ReadStartElement("root");

    reader.ReadStartElement("EmptyElement");

    reader.ReadStartElement("NonEmptyElement");

    while (reader.ReadToNextSibling("SubEmptyElement"))
    {
        // ...
    }

    reader.ReadEndElement(/* NonEmptyElement */);

    reader.ReadEndElement(/* root */);
    // ...
}

如果您只想跳过<EmptyElement>中的任何内容,无论它是否实际为空,请使用ReadToFollowing

代码语言:javascript
运行
复制
public static void ReadData(XmlReader reader)
{
    reader.ReadStartElement("root");

    reader.ReadToFollowing("NonEmptyElement");

    Console.WriteLine(reader.GetAttribute("Name"));

    reader.ReadStartElement("NonEmptyElement");

    Console.WriteLine(reader.GetAttribute("Name"));
    while (reader.ReadToNextSibling("SubEmptyElement"))
    {
        // ...
    }

    reader.ReadEndElement(/* NonEmptyElement */);

    reader.ReadEndElement(/* root */);
    // ...
}

更新:这里有一个更完整的示例,其中有一个更清晰的数据模型。也许这更接近你的要求。

XMLFile1.xml:

代码语言:javascript
运行
复制
<?xml version="1.0" encoding="utf-8" standalone="no"?>
<root>
  <Person Type="Homeless"/>
  <Person Type="Developer">
    <Home Type="Apartment" />
  </Person>
  <Person Type="Banker">
    <Home Type="Apartment"/>
    <Home Type="Detached"/>
    <Home Type="Mansion">
      <PoolHouse/>
    </Home>
  </Person>
</root>

Program.cs:

代码语言:javascript
运行
复制
using System;
using System.Xml;

namespace ConsoleApplication6
{
    internal class Program
    {
        public static void ReadData(XmlReader reader)
        {
            reader.ReadStartElement("root");

            while (reader.IsStartElement("Person"))
            {
                ReadPerson(reader);
            }

            reader.ReadEndElement( /* root */);
        }

        public static void ReadPerson(XmlReader reader)
        {
            Console.WriteLine(reader.GetAttribute("Type"));
            bool isEmpty = reader.IsEmptyElement;
            reader.ReadStartElement("Person");
            while (reader.IsStartElement("Home"))
            {
                ReadHome(reader);
            }
            if (!isEmpty)
            {
                reader.ReadEndElement( /* Person */);
            }
        }

        public static void ReadHome(XmlReader reader)
        {
            Console.WriteLine("\t" + reader.GetAttribute("Type"));
            bool isEmpty = reader.IsEmptyElement;
            reader.ReadStartElement("Home");

            if (!isEmpty)
            {
                reader.Skip();
                reader.ReadEndElement( /* Home */);
            }
        }

        private static void Main(string[] args)
        {
            var settings = new XmlReaderSettings { IgnoreWhitespace = true };
            using (var xr = XmlReader.Create("XMLFile1.xml", settings))
            {
                ReadData(xr);
            }
            Console.ReadKey();
        }
    }
}
票数 7
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/4982251

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档