从 URL 使用 C# 反序列化 XML

本文关键字:反序列化 XML 使用 URL | 更新日期: 2023-09-27 18:31:51

我正在从网站中提取XML站点地图来解析它。

最简单的方法是将其反序列化为 on objet。

我在示例代码的最后一行抛出错误"XML文档中的错误"。有谁知道为什么。错误消息中没有更多详细信息。

到目前为止我的代码:

[Serializable, XmlRoot("urlset")]
public class Urlset
{
    public B5_Url[] urls;
}
[XmlType("url")]
public class B5_Url
{
    [XmlElement("loc")]
    public string loc;
    [XmlElement("lastmod")]
    public string lastmod;
    [XmlElement("changefreq")]
    public string changefreq;
}
class Program
{
    static void Main(string[] args)
    {
        string url = "http://www.myurl.de/sitemap.xml";
        XmlSerializer ser = new XmlSerializer(typeof(Urlset));
        WebClient client = new WebClient();
        string data = Encoding.Default.GetString(client.DownloadData(url));
        Stream stream = new MemoryStream(Encoding.UTF8.GetBytes(data));
        Urlset reply = (Urlset)ser.Deserialize(stream);  
    }
}

这是 XML:

<?xml version="1.0" encoding="UTF-8"?>
<urlset xmlns="http://www.sitemaps.org/schemas/sitemap/0.9" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://www.sitemaps.org/schemas/sitemap/0.9             http://www.sitemaps.org/schemas/sitemap/0.9/sitemap.xsd">
<url>
  <loc>http://www.myurl.de/</loc>
  <lastmod>2012-06-25T17:10:30+00:00</lastmod>
  <changefreq>always</changefreq>
</url>
</urlset>

感谢您的帮助:)

从 URL 使用 C# 反序列化 XML

你应该按照@vitalygolub的建议去做。此外,由于根元素中设置了命名空间,您仍然会收到错误。要修复它:

[XmlRoot("urlset", Namespace="http://www.sitemaps.org/schemas/sitemap/0.9")]
public class Urlset
{
    [XmlElement("url")]
    public B5_Url[] urlset;
}
public class B5_Url
{
    [XmlElement("loc")]
    public string loc;
    [XmlElement("lastmod")]
    public string lastmod;
    [XmlElement("changefreq")]
    public string changefreq;
}

我测试了这段代码,它适用于您的输入。

如果这是您的 XML,则缺少结束</url>

<?xml version="1.0" encoding="UTF-8"?>
<urlset xmlns="http://www.sitemaps.org/schemas/sitemap/0.9" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://www.sitemaps.org/schemas/sitemap/0.9             http://www.sitemaps.org/schemas/sitemap/0.9/sitemap.xsd">
<url>
  <loc>http://www.myurl.de/</loc>
  <lastmod>2012-06-25T17:10:30+00:00</lastmod>
  <changefreq>always</changefreq>
</url>
</urlset>

我收到错误<urlset xmlns='http://www.sitemaps.org/schemas/sitemap/0.9'> was not expected.

改变:

<urlset xmlns="http://www.sitemaps.org/schemas/sitemap/0.9" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://www.sitemaps.org/schemas/sitemap/0.9 http://www.sitemaps.org/schemas/sitemap/0.9/sitemap.xsd">

<urlset>

让它没有出错。

这是我的工作 linqpad 示例

[Serializable, System.Xml.Serialization.XmlRoot("urlset")]
public class Urlset
{
    [System.Xml.Serialization.XmlElement("url")]
    public B5_Url[] urls;
}
[System.Xml.Serialization.XmlType("url")]
public class B5_Url
{
    [System.Xml.Serialization.XmlElement("loc")]
    public string loc;
    [System.Xml.Serialization.XmlElement("lastmod")]
    public string lastmod;
    [System.Xml.Serialization.XmlElement("changefreq")]
    public string changefreq;
}
class Program
{
    static void Main(string[] args)
    {
        var data = "<?xml version='"1.0'" encoding='"UTF-8'"?><urlset><url><loc>http://www.myurl.de/</loc><lastmod>2012-06-25T17:10:30+00:00</lastmod><changefreq>always</changefreq></url></urlset>";
        var ser = new System.Xml.Serialization.XmlSerializer(typeof(Urlset));
        Stream stream = new MemoryStream(Encoding.UTF8.GetBytes(data));
        Urlset reply = (Urlset)ser.Deserialize(stream);  
        reply.Dump();
    }
}

我必须进行的另一个更改是 B5_Url[] 数组上的 [System.Xml.Serialization.XmlElement("url")] 属性 UrlSet

您必须提供以下内容

[Serializable, XmlRoot("urlset")]
public class Urlset
{
    [XmlElement("url")]
    public B5_Url[] urls;
}

这会将集合中的每个元素直接序列化到根元素中,而不是urls元素。

编辑:但是,您可以从B5_Url中省略XmlType属性。

这可能是因为你的类将被序列化为这个 xml

<?xml version="1.0"?>
<urlset xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:xsd="http://www.w3.org/2001/XMLSchema">
  <urls>
    <url>
      <loc>http://www.myurl.de/</loc>
      <lastmod>2012-06-25T17:10:30+00:00</lastmod>
      <changefreq>always</changefreq>
    </url>
  </urls>
</urlset>

尝试像这样更改

[Serializable, XmlRoot("urlset")]
    public class Urlset
    {
        [XmlElement("urlset") ]  //should be here
        public B5_Url[] urls;
    }
    [XmlType("url")]
    public class B5_Url
    {
        [XmlElement("loc")]
        public string loc;
        [XmlElement("lastmod")]
        public string lastmod;
        [XmlElement("changefreq")]
        public string changefreq;
    }
相关文章: