Warning: file_get_contents(/data/phpspider/zhask/data//catemap/2/.net/20.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181

Warning: file_get_contents(/data/phpspider/zhask/data//catemap/0/xml/12.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181

Warning: file_get_contents(/data/phpspider/zhask/data//catemap/0/mercurial/2.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
.net 如何序列化只包含“的字符串”\r\n“;正确地使用XML?_.net_Xml - Fatal编程技术网

.net 如何序列化只包含“的字符串”\r\n“;正确地使用XML?

.net 如何序列化只包含“的字符串”\r\n“;正确地使用XML?,.net,xml,.net,Xml,我们正在使用DataContractSerializer将数据序列化为XML。最近,我们发现了一个关于字符串“\r\n”如何保存和读回的错误-它变成了“\n”。显然,导致这种情况的原因是使用XmlWriter和Indent=true集合: // public class Test { public string Line; } var serializer = new DataContractSerializer(typeof(Test)); using (var fs = File.Ope

我们正在使用
DataContractSerializer
将数据序列化为XML。最近,我们发现了一个关于字符串
“\r\n”
如何保存和读回的错误-它变成了
“\n”
。显然,导致这种情况的原因是使用
XmlWriter
Indent=true
集合:

// public class Test { public string Line; }

var serializer = new DataContractSerializer(typeof(Test));

using (var fs = File.Open("C:/test.xml", FileMode.Create))
using (var wr = XmlWriter.Create(fs, new XmlWriterSettings() { Indent = true }))
    serializer.WriteObject(wr, new Test() { Line = "\r\n" });

Test test;
using (var fs = File.Open("C:/test.xml", FileMode.Open))
    test = (Test) serializer.ReadObject(fs);
显而易见的解决方法是停止缩进XML,并确实删除“
XmlWriter.Create
”行使
值正确往返,无论是
“\n”
“\r\n”
还是其他任何内容

但是,
DataContractSerializer
编写它的方式似乎仍然不完全安全,甚至可能不正确-例如,仅使用XML记事本读取结果文件并再次保存它,就会完全破坏
“\n”
“\r\n”


这里的正确方法是什么?使用XML作为序列化二进制数据的格式是一个有缺陷的概念吗?我们期望像XML记事本这样的工具不会破坏我们的数据,这是错误的吗?我们是否需要用一些特殊属性来扩充每个
字符串
字段,这些字段可能包含这样的文本,也许是强制CDATA的原因?

您可能会使用CDATA,但我同意您的总结,即使用XML序列化二进制数据是完全错误的。您可以用另一种方式传递数据吗?

为什么区分包含“\r\n”的字符串和空字符串很重要?通常,在使用数据协定序列化时,只要数据“往返”正确,就不关心XML格式/结构或它如何存储数据

我们就是这样使用它的:

DataContractSerializer serializer = CreateSerializer(this.GetType());
XmlWriterSettings settings = new XmlWriterSettings();
settings.Indent = true;
using (XmlWriter writer = XmlTextWriter.Create(sb, settings))
{
   serializer.WriteObject(writer, this);
   writer.Flush();
}


internal static T Deserialize<T>(Stream stream)
{
   DataContractSerializer serializer = CreateSerializer(typeof(T));
   return (T)serializer.ReadObject(stream);
}

public static DataContractSerializer CreateSerializer(Type type)
{
   DataContractSerializer serializer = new DataContractSerializer();
   return serializer;
}
DataContractSerializer-serializer=CreateSerializer(this.GetType());
XmlWriterSettings=新的XmlWriterSettings();
settings.Indent=true;
使用(XmlWriter=XmlTextWriter.Create(sb,设置))
{
serializer.WriteObject(writer,this);
writer.Flush();
}
内部静态T反序列化(流)
{
DataContractSerializer serializer=CreateSerializer(typeof(T));
return(T)serializer.ReadObject(stream);
}
公共静态DataContractSerializer CreateSerializer(类型)
{
DataContractSerializer serializer=新的DataContractSerializer();
返回序列化程序;
}
如果我没有弄错的话,像linefeed这样的字符是XML值中不允许使用的字符,需要在CDATA节中进行编码或对其进行约束。数据协定序列化程序不执行这两项操作。像XMLNotepad这样的工具正在更改数据,因为它们意识到这些不是合法字符,并将它们删除以创建一致的XML

实际上,二进制序列化程序和XML序列化程序返回的字符串数据可能不同,这并不奇怪。二进制序列化程序将逐位序列化数据的精确二进制表示,并且没有关于什么是合法字符等的“规则”。

您可以尝试使用:

XmlWriterSettings.NewLineHandling=NewLineHandling.Entitize;

那么,您认为使用DataContractSerializer并期望获得与您保存的数据完全相同的数据是一个bug吗?我怀疑在您检查CDATA部分是否处理它之前,它不能被称为bug。换行符是一种边缘情况,因为很明显,您的系统上的换行符不一定与我的系统上的相同,所以我可以原谅这样的实现。我会尝试强制使用CDATA方法。好吧,作为记录,最后我们停止缩进XML。很丑,;使用XML作为数据存储格式,而XML显然是一种文档标记格式。为什么区分很重要?有时不重要,有时重要。从BinaryFormatter迁移过来后,我们惊奇地发现字符串现在可以以不同的方式保存起来。>>“您不关心XML格式/结构”——事实上;然而,看到XML记事本更改我们的数据令人担忧,让我想知道我们做错了什么。@romkyns:更新了我的答案以解决您的问题。总的来说,只要对象反序列化正确,我不认为您做了任何“错误”的事情。我仍然不明白为什么需要区分空行('\r\n')和空字符串。我也理解这个问题。如果通过包含CRLF的连线对字符串进行xml序列化,则收件人将只获得LF。它不是往返的!