通过StreamReader / StreamWriter打开和保存时,XmlDocument出现乱码

时间:2014-01-23 17:40:19

标签: c# xml winforms .net-4.5 filestream

我在C#中有一个使用XML配置文件的WinForms应用程序。

为了防止其他应用和用户在应用运行时编辑这些文件,我使用了...

打开文档:

document = new XmlDocument();

using ( var xr = new StreamReader( new FileStream( fileName, FileMode.Open, FileAccess.ReadWrite, FileShare.Read ), Encoding.UTF8 ) )
{
    document.Load( xr );
}

...一个Save()方法,它使用writer再次保存文件。

lock ( syncLock )
{
    using ( var writer = XmlTextWriter.Create( new FileStream( fileName, FileMode.Open, FileAccess.ReadWrite, FileShare.Read ), settings ) )
    {
        document.Save( writer );
    }
}

由于多个线程可能希望保存到文件,因此存在锁定。我实际上不确定这是否有任何意义。

当我为了isntance,从DOM树中删除一个节点然后保存文件时,该文件就变成了垃圾。

这个好文件......

<?xml version="1.0" encoding="utf-8"?>
<history>
  <period something="2013-01-01 04:55:12" added="2013-01-01 04:58:12" />
  <period something="2013-01-01 10:55:12" added="2013-01-01 10:58:12" />
  <period something="2013-01-01 16:55:12" added="2013-01-01 16:58:12" />
  <period something="2013-01-01 22:55:12" added="2013-01-01 22:58:12" />
  <period something="2013-01-02 04:55:12" added="2013-01-02 04:58:12" />
  <period something="2013-01-02 10:55:12" added="2013-01-02 10:58:12" />
  <period something="2013-01-02 16:55:12" added="2013-01-02 16:58:12" />
  <period something="2013-01-02 22:55:12" added="2013-01-02 22:58:12" />
</history>

......变成了这个:

<?xml version="1.0" encoding="utf-8"?>
<history>
  <period something="2013-01-01 04:55:12" added="2013-01-01 04:58:12" />
  <period something="2013-01-01 10:55:12" added="2013-01-01 10:58:12" />
  <period something="2013-01-01 16:55:12" added="2013-01-01 16:58:12" />
  <period something="2013-01-01 22:55:12" added="2013-01-01 22:58:12" />
  <period something="2013-01-02 04:55:12" added="2013-01-02 04:58:12" />
  <period something="2013-01-02 10:55:12" added="2013-01-02 10:58:12" />
  <period something="2013-01-02 16:55:12" added="2013-01-02 16:58:12" />
</history>/>
    <period something="2013-01-02 22:55:12" added="2013-01-02 22:58:12" />
</history>

因此我删除的节点又回来了,但文档不再格式良好。

为什么呢? 有什么想法吗?

1 个答案:

答案 0 :(得分:1)

这是问题所在:

new FileStream( fileName, FileMode.Open, FileAccess.ReadWrite, FileShare.ReadWrite )

如果该文件已存在,则会覆盖现有文件,但不会截断它。

您应该指定FileMode.Create ...或更简单,只需使用File.Create来获取流。更好的是,不要打扰StreamWriterStreamReaer,甚至不要手动创建流。哎呀,当加载文件时,您只需指定文件名:

document = new XmlDocument();
document.Load(fileName);

如果你真的需要自定义设置,那么为了保存:

using (var writer = XmlWriter.Create(fileName, settings))
{
    document.Save(writer);
}    

我会强烈建议您在编写文件时阻止从文件中读取 - 顺便说一句 - 在编写文件时,它无论如何都不会是有效的XML文件。

如果可能的话,我还建议你从XmlDocument迁移到LINQ到XML(XDocument等) - 这是一个更好的API。