C# 使用具有 ISO-8859-1 编码的 XmlTextWriter 编写 XML 文件

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/139260/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me): StackOverFlow

提示:将鼠标放在中文语句上可以显示对应的英文。显示中英文
时间:2020-08-03 15:09:58  来源:igfitidea点击:

Writing XML files using XmlTextWriter with ISO-8859-1 encoding

提问by henningst

I'm having a problem writing Norwegian characters into an XML file using C#. I have a string variable containing some Norwegian text (with letters like ???).

我在使用 C# 将挪威语字符写入 XML 文件时遇到问题。我有一个字符串变量,其中包含一些挪威语文本(带有诸如 ??? 之类的字母)。

I'm writing the XML using an XmlTextWriter, writing the contents to a MemoryStream like this:

我正在使用 XmlTextWriter 编写 XML,将内容写入 MemoryStream,如下所示:

MemoryStream stream = new MemoryStream();
XmlTextWriter xmlTextWriter = new XmlTextWriter(stream, Encoding.GetEncoding("ISO-8859-1"));
xmlTextWriter.Formatting = Formatting.Indented;
xmlTextWriter.WriteStartDocument(); //Start doc

Then I add my Norwegian text like this:

然后我像这样添加我的挪威语文本:

xmlTextWriter.WriteCData(myNorwegianText);

Then I write the file to disk like this:

然后我将文件写入磁盘,如下所示:

FileStream myFile = new FileStream(myPath, FileMode.Create);
StreamWriter sw = new StreamWriter(myFile);

stream.Position = 0;
StreamReader sr = new StreamReader(stream);
string content = sr.ReadToEnd();

sw.Write(content);
sw.Flush();

myFile.Flush();
myFile.Close();

Now the problem is that in the file on this, all the Norwegian characters look funny.

现在的问题是,在这个文件中,所有的挪威字符看起来都很有趣。

I'm probably doing the above in some stupid way. Any suggestions on how to fix it?

我可能正在以某种愚蠢的方式执行上述操作。有关如何修复它的任何建议?

采纳答案by tomasr

Why are you writing the XML first to a MemoryStream and then writing that to the actual file stream? That's pretty inefficient. If you write directly to the FileStream it should work.

为什么要先将 XML 写入 MemoryStream,然后再将其写入实际的文件流?这是相当低效的。如果您直接写入 FileStream 它应该可以工作。

If you still want to do the double write, for whatever reason, do one of two things. Either

如果您仍然想进行双重写入,无论出于何种原因,请执行以下两项操作之一。任何一个

  1. Make sure that the StreamReader and StreamWriter objects you use alluse the sameencoding as the one you used with the XmlWriter (not just the StreamWriter, like someone else suggested), or

  2. Don't use StreamReader/StreamWriter. Instead just copy the stream at the byte level using a simple byte[] and Stream.Read/Write. This is going to be, btw, a lot more efficient anyway.

  1. 确保您使用的 StreamReader 和 StreamWriter 对象使用您与 XmlWriter 一起使用的编码相同的编码(不仅仅是 StreamWriter,就像其他人建议的那样),或者

  2. 不要使用 StreamReader/StreamWriter。相反,只需使用简单的 byte[] 和 Stream.Read/Write 在字节级别复制流。顺便说一句,无论如何,这将更有效率。

回答by Treb

Which encoding do you use for displaying the result file? If it is not in ISO-8859-1, it will not display correctly.

您使用哪种编码来显示结果文件?如果它不在 ISO-8859-1 中,它将无法正确显示。

Is there a reason to use this specific encoding, instead of for example UTF8?

是否有理由使用这种特定的编码,而不是例如 UTF8?

回答by Jon Skeet

Both your StreamWriter and your StreamReader are using UTF-8, because you're not specifying the encoding. That's why things are getting corrupted.

您的 StreamWriter 和 StreamReader 都使用 UTF-8,因为您没有指定编码。这就是为什么事情会被破坏。

As tomasr said, using a FileStream to start with would be simpler - but also MemoryStream has the handy "WriteTo" method which lets you copy it to a FileStream very easily.

正如 tomasr 所说,使用 FileStream 开始会更简单 - 但 MemoryStream 还具有方便的“WriteTo”方法,可让您非常轻松地将其复制到 FileStream。

I hope you've got a using statement in your real code, by the way - you don't want to leave your file handle open if something goes wrong while you're writing to it.

顺便说一下,我希望您的实际代码中有一个 using 语句 - 如果在写入文件时出现问题,您不想让文件句柄保持打开状态。

Jon

乔恩

回答by Thomas Danecker

You need to set the encoding everytime you write a string or read binary data as a string.

每次写入字符串或将二进制数据作为字符串读取时,都需要设置编码。

    Encoding encoding = Encoding.GetEncoding("ISO-8859-1");

    FileStream myFile = new FileStream(myPath, FileMode.Create);
    StreamWriter sw = new StreamWriter(myFile, encoding);

    stream.Position = 0;
    StreamReader sr = new StreamReader(stream, encoding);
    string content = sr.ReadToEnd();

    sw.Write(content);
    sw.Flush();

    myFile.Flush();
    myFile.Close();

回答by Troy Alford

As mentioned in above answers, the biggest issue here is the Encoding, which is being defaulted due to being unspecified.

正如上面的答案中提到的,这里最大的问题是Encoding,由于未指定而被默认。

When you do not specify an Encodingfor this kind of conversion, the default of UTF-8is used - which may or may not match your scenario. You are also converting the data needlessly by pushing it into a MemoryStreamand then out into a FileStream.

当您没有Encoding为这种类型的转换指定 an 时,将使用默认的 of UTF-8- 这可能与您的场景相匹配,也可能不匹配。您还通过将数据推入 aMemoryStream然后再推入 a 来不必要地转换数据FileStream

If your original data is not UTF-8, what will happen here is that the first transition into the MemoryStreamwill attempt to decode using default Encodingof UTF-8- and corrupt your data as a result. When you then write out to the FileStream, which is also using UTF-8as encoding by default, you simply persist that corruption into the file.

如果你的原始数据是不是UTF-8,有什么会发生在这里是第一过渡到MemoryStream将尝试使用默认解码EncodingUTF-8-并破坏你的数据结果。当您写入 . 时,默认情况下FileStream它也UTF-8用作编码,您只需将该损坏保留到文件中。

In order to fix the issue, you likely need to specify Encodinginto your Streamobjects.

为了解决这个问题,您可能需要EncodingStream对象中指定。

You can actually skip the MemoryStreamprocess entirely, also - which will be faster and more efficient. Your updated code might look something more like:

您实际上MemoryStream也可以完全跳过该过程 - 这将更快、更有效。您更新后的代码可能看起来更像:

FileStream fs = new FileStream(myPath, FileMode.Create);

XmlTextWriter xmlTextWriter = 
    new XmlTextWriter(fs, Encoding.GetEncoding("ISO-8859-1"));

xmlTextWriter.Formatting = Formatting.Indented;
xmlTextWriter.WriteStartDocument(); //Start doc

xmlTextWriter.WriteCData(myNorwegianText);

StreamWriter sw = new StreamWriter(fs);

fs.Position = 0;
StreamReader sr = new StreamReader(fs);
string content = sr.ReadToEnd();

sw.Write(content);
sw.Flush();

fs.Flush();
fs.Close();

回答by mauro.Joestar

After investigating, this is that worked best for me:

经过调查,这是最适合我的:

var doc = new XDocument(new XDeclaration("1.0", "ISO-8859-1", ""));
        using (XmlWriter writer = doc.CreateWriter()){
            writer.WriteStartDocument();
            writer.WriteStartElement("Root");
            writer.WriteElementString("Foo", "value");
            writer.WriteEndElement();
            writer.WriteEndDocument();
        }
        doc.Save("dte.xml");