我的数据实体包含一个Dictionary,但XmlSerializer不支持开箱即用。所以我决定使用DataContractSerializer。问题是我不能让它按照我的需要行事。
我从以下代码开始:
public static string SerializeObject<T>(T serialisable)
{
var serializer = new DataContractSerializer(serialisable.GetType());
using (var writer = new StringWriter())
using (var stm = new XmlTextWriter(writer))
{
serializer.WriteObject(stm, serialisable);
return writer.ToString();
}
}
似乎工作正常,直到我注意到如果我将“\ r \ n”放在字符串中,它就不会被序列化为XML实体。根据我使用XmlSerializer的经验,我知道我可以使用NewLineHandling = NewLineHandling.Entitize设置XmlWriterSettings。所以我将我的代码转换为以下内容:
public static string SerializeObject<T>(T serialisable)
{
var serializer = new DataContractSerializer(serialisable.GetType());
using (var writer = new StringWriter())
{
using (var stm = XmlWriter.Create(writer,
new XmlWriterSettings()
{
NewLineHandling = NewLineHandling.Entitize
}))
{
serializer.WriteObject(stm, serialisable);
return writer.ToString();
}
}
}
现在的问题是我得到一个空字符串。没有例外,没有 - 只是一个空字符串。 stm变量包含XmlWellFormedWriter。也许DataContractSerializer不支持它?
然后我尝试按如下方式强制执行XmlTextWriter:
public static string SerializeObject<T>(T serialisable)
{
var serializer = new DataContractSerializer(serialisable.GetType());
using (var writer = new StringWriter())
using (var stm = XmlWriter.Create(new XmlTextWriter(writer),
new XmlWriterSettings()
{
NewLineHandling = NewLineHandling.Entitize
}))
{
serializer.WriteObject(stm, serialisable);
return writer.ToString();
}
}
这让我回到我开始的地方 - 我找回了XML字符串,但是再次“\ r \ n”字符串未转换为实体。
如何让DataContractSerializer授权换行并将XML作为字符串返回?
答案 0 :(得分:2)
我知道这是一个非常古老的帖子,但我偶然发现它正在寻找答案,并认为我会回答我发现的问题。
\ n未被授权的原因是因为它们位于文本节点值中。如果序列化程序属于属性,则序列化程序将仅授权\ n个字符。
以下是我在每个NewLineHandling值中发现的内容
文字节点
NewLineHandling.Replace (Default)
\r \n \r\n all go to \r\n
\t remains as \t
NewLineHandling.Entitize
\r\n goes to &#D;
\n remains as \n
\r goes to &#D;
\t remains as \t
NewLineHandling.None
\r remains \r
\r\n remains \n
\r\n remains \r\n
\t remains as \t
的属性强> 的
NewLineHandling.Replace (Default)
\r\n goes to &#D;&#A;
\n goes to &#A;
\r goes to &#D;
\t remains 	
NewLineHandling.Entitize
\r\n goes to &#D;&#A;
\n goes to &#A;
\r goes to &#D;
\t remains 	
NewLineHandling.None
\r remains \r
\r\n remains as \n
\r\n remains as \r\n
\t remains as \t
答案 1 :(得分:0)
看来,问题主要是因为处理XmlWriter的工作原理 - 如果我使用XmlWriter.Create创建它,它在关闭之前不会刷新,所以StringWriter为空。有什么奇怪的 - 如果我用新的XmlTextWriter创建它,它会以某种方式将其内容刷新到StringWriter,所以我的初始方法工作正常。
这次我只需要重新排列一行代码:
public static string SerializeObject<T>(T serialisable)
{
var serializer = new DataContractSerializer(serialisable.GetType());
using (var writer = new StringWriter())
{
using (var stm = XmlWriter.Create(writer,
new XmlWriterSettings()
{
NewLineHandling = NewLineHandling.Entitize,
Encoding = UTF8Encoding.UTF8
}))
{
serializer.WriteObject(stm, serialisable);
// <- previously writer.ToString() was here and I got an empty string
}
return writer.ToString();
}
}
现在“\ r”字符被正确编码为
,但“\ n”不是。编码仍然是utf-16,虽然我把它设置为UTF8。我想,这是另一个问题。