2

我想提供一种在应用程序中保存工作的方法。这是一种项目功能。项目需要序列化为 XML。我已经让 DataContractSerializer 生成 XML,但我需要能够在 XML 文件中选择一个位置以使其序列化,而不是为自己编写一个完整的文件,因为将有多个项目,我需要能够从 Projects XML 文件中单独反序列化这些项目。

我想要的 XML:

<Projects>
    <Project>
        <ID>...</ID>
        <Name>...</Name>
        <LastEdited>...</LastEdited>
        ...
    </Project>
    <Project>...</Project>
    <Project>...</Project>
</Projects>

然后,我将使用 Linq to XML 根据项目 ID 进行序列化和反序列化以导航文档。

有什么建议么?非常感谢提前。

4

1 回答 1

1

找到了一种方法来做到这一点。它有它的障碍,但是一旦你把所有东西都包括在内,它就会非常顺利地工作。

要生成 XML:

DataContractSerializer ser = new DataContractSerializer(typeof(Project));
StringBuilder objectSB = new StringBuilder();
XmlWriter objectWriter = XmlWriter.Create(objectSB);
//I'm using this method in the object I want to serialize (hence the 'this')
ser.WriteObject(objectWriter, this);
objectWriter.Flush();

然后,您可以将 StringBuilder 转换为 Linq to XML 的 XElement:

Xelement xProject = Xelement.Parse(objectSB.ToString());

对于反序列化:

DataContractSerializer ser = new DataContractSerializer(typeof(Project));
Project project = (CoilProject)ser.ReadObject(xProject.CreateReader());

有几次我使用 Linq to XML 编辑 XML 而不进行反序列化和重新序列化。由于 DataContractSerializer 添加的命名空间,这变得很有必要:

//place this somewhere in your project's namespace
public static class MyExtensions
{
    public static IEnumerable<XElement> ElementsAnyNS(this XElement source, string localName)
    {
        return source.Elements().Where(e => e.Name.LocalName == localName);
    }

    public static XElement ElementAnyNS(this XElement source, string localName)
    {
        return source.Elements().Where(e => e.Name.LocalName == localName).Select(e => e).Single();
    }
}

这些扩展方法允许您从序列化对象中选择一个或多个元素,而无需担心命名空间。我从Pavel MinaevIgnore namespaces in LINQ to XML的回答中改编了这些扩展方法。

于 2012-07-24T16:38:58.003 回答