2

我正在为新闻门户开发 WP 应用程序,我需要解析各种提要。标准提要如下所示:

<feed>
    <items>
        <item>
            ...
        </item>
        <item>
            ...
        </item>
    </items>
</feed>

我使用这段代码来反序列化它:

XDocument document = XDocument.Load(xmlStream);
XmlSerializer serializer = new XmlSerializer(typeof(News));
News MainPage = (News)serializer.Deserialize(document.CreateReader());
Dispatcher.BeginInvoke(() => MainPageListBox.ItemsSource = MainPage.DataSet;);

新闻类如下所示:

[XmlRoot("feed")]
public class News
{
    [XmlArray("items")]
    [XmlArrayItem("item")]
    public ObservableCollection<NewsItem> DataSet{ get; set; }
}

这在具有这种结构的每个提要中都可以正常工作<items>。但我也有多个部分的提要,例如:

<feed>
    <items section="part 1">
        <item>
            ...
        </item>
        <item>
            ...
        </item>
    </items>
    <items section="part 2">
        <item>
            ...
        </item>
        <item>
            ...
        </item>
    </items>
</feed>

如果我使用上面的 C# 代码,则只<items>解析第一部分,忽略其他部分。我需要为<items>单个 XML 提要中的每个部分创建单独的 List 或 ObservableCollection。

谁能帮我这个?非常感谢。

4

1 回答 1

2

课程:

[XmlRoot("feed")]
    public class News
    {
        [XmlArray("items")]
        public List<NewsItemCollection> DataSet { get; set; }

        public News()
        {
            DataSet = new List<NewsItemCollection>();
        }
    }

    public class NewsItemCollection
    {
        [XmlAttribute("section")]
        public string Section { get; set; }

        [XmlElement("item")]
        public ObservableCollection<NewsItem> Items { get; set; }

        public NewsItemCollection()
        {
            Items = new ObservableCollection<NewsItem>();
        }
    }

    public class NewsItem
    {
        public string Title { get; set; }
    }

我的一些用于序列化/反序列化 xml 的辅助类:

public static class ObjectExtensions
    {
        /// <summary>
        /// <para>Serializes the specified System.Object and writes the XML document</para>
        /// <para>to the specified file.</para>
        /// </summary>
        /// <typeparam name="T">This item's type</typeparam>
        /// <param name="item">This item</param>
        /// <param name="fileName">The file to which you want to write.</param>
        /// <returns>true if successful, otherwise false.</returns>
        public static bool XmlSerialize<T>(this T item, string fileName)
        {
            return item.XmlSerialize(fileName, true);
        }

        /// <summary>
        /// <para>Serializes the specified System.Object and writes the XML document</para>
        /// <para>to the specified file.</para>
        /// </summary>
        /// <typeparam name="T">This item's type</typeparam>
        /// <param name="item">This item</param>
        /// <param name="fileName">The file to which you want to write.</param>
        /// <param name="removeNamespaces">
        ///     <para>Specify whether to remove xml namespaces.</para>para>
        ///     <para>If your object has any XmlInclude attributes, then set this to false</para>
        /// </param>
        /// <returns>true if successful, otherwise false.</returns>
        public static bool XmlSerialize<T>(this T item, string fileName, bool removeNamespaces)
        {
            object locker = new object();

            XmlSerializerNamespaces xmlns = new XmlSerializerNamespaces();
            xmlns.Add(string.Empty, string.Empty);

            XmlSerializer xmlSerializer = new XmlSerializer(typeof(T));

            XmlWriterSettings settings = new XmlWriterSettings();
            settings.Indent = true;
            settings.OmitXmlDeclaration = true;

            lock (locker)
            {
                using (XmlWriter writer = XmlWriter.Create(fileName, settings))
                {
                    if (removeNamespaces)
                    {
                        xmlSerializer.Serialize(writer, item, xmlns);
                    }
                    else { xmlSerializer.Serialize(writer, item); }

                    writer.Close();
                }
            }

            return true;
        }

        /// <summary>
        /// Serializes the specified System.Object and returns the serialized XML
        /// </summary>
        /// <typeparam name="T">This item's type</typeparam>
        /// <param name="item">This item</param>
        /// <returns>Serialized XML for specified System.Object</returns>
        public static string XmlSerialize<T>(this T item)
        {
            return item.XmlSerialize(true);
        }

        /// <summary>
        /// Serializes the specified System.Object and returns the serialized XML
        /// </summary>
        /// <typeparam name="T">This item's type</typeparam>
        /// <param name="item">This item</param>
        /// <param name="removeNamespaces">
        ///     <para>Specify whether to remove xml namespaces.</para>para>
        ///     <para>If your object has any XmlInclude attributes, then set this to false</para>
        /// </param>
        /// <returns>Serialized XML for specified System.Object</returns>
        public static string XmlSerialize<T>(this T item, bool removeNamespaces)
        {
            object locker = new object();

            XmlSerializerNamespaces xmlns = new XmlSerializerNamespaces();
            xmlns.Add(string.Empty, string.Empty);

            XmlSerializer xmlSerializer = new XmlSerializer(typeof(T));

            XmlWriterSettings settings = new XmlWriterSettings();
            settings.Indent = true;
            settings.OmitXmlDeclaration = true;

            lock (locker)
            {
                StringBuilder stringBuilder = new StringBuilder();
                using (StringWriter stringWriter = new StringWriter(stringBuilder))
                {
                    using (XmlWriter xmlWriter = XmlWriter.Create(stringWriter, settings))
                    {
                        if (removeNamespaces)
                        {
                            xmlSerializer.Serialize(xmlWriter, item, xmlns);
                        }
                        else { xmlSerializer.Serialize(xmlWriter, item); }

                        return stringBuilder.ToString();
                    }
                }
            }
        }
    }

public static class StringExtensions
    {
        /// <summary>
        /// Deserializes the XML data contained by the specified System.String
        /// </summary>
        /// <typeparam name="T">The type of System.Object to be deserialized</typeparam>
        /// <param name="s">The System.String containing XML data</param>
        /// <returns>The System.Object being deserialized.</returns>
        public static T XmlDeserialize<T>(this string s)
        {
            var locker = new object();
            var stringReader = new StringReader(s);
            var reader = new XmlTextReader(stringReader);
            try
            {
                var xmlSerializer = new XmlSerializer(typeof(T));
                lock (locker)
                {
                    var item = (T)xmlSerializer.Deserialize(reader);
                    reader.Close();
                    return item;
                }
            }
            catch
            {
                return default(T);
            }
            finally
            {
                reader.Close();
            }
        }
    }

测试运行:

News news = new News();
            news.DataSet.Add(new NewsItemCollection
            {
                Section = "Section1",
                Items = new ObservableCollection<NewsItem>
                    {
                        new NewsItem { Title = "Test1.1" },
                        new NewsItem { Title = "Test1.2" }
                    }
            });
            news.DataSet.Add(new NewsItemCollection
            {
                Section = "Section2",
                Items = new ObservableCollection<NewsItem>
                    {
                        new NewsItem { Title = "Test2.1" },
                        new NewsItem { Title = "Test2.2" }
                    }
            });

            var serialized = news.XmlSerialize();
            var deserialized = serialized.XmlDeserialize<News>();

玩得开心!

于 2012-07-18T06:53:20.103 回答