C# DataContractSerializer创建的XML格式
有没有一种简单的方法让DataContractSerializer吐出格式化的XML而不是一个长字符串?我不想以任何方式更改标记或内容,只是让它添加换行符和缩进以使XML更具可读性C# DataContractSerializer创建的XML格式,c#,xml,formatting,datacontractserializer,C#,Xml,Formatting,Datacontractserializer,有没有一种简单的方法让DataContractSerializer吐出格式化的XML而不是一个长字符串?我不想以任何方式更改标记或内容,只是让它添加换行符和缩进以使XML更具可读性 <tagA> <tagB>This is</tagB> <tagC>Much</tagC> <tagD> <tagE>easier to read</tagE> </tagD
<tagA>
<tagB>This is</tagB>
<tagC>Much</tagC>
<tagD>
<tagE>easier to read</tagE>
</tagD>
</tagA>
<tagA><tagB>This is</tagB><tagC>Much</tagC><tagD><tagE>harder to read</tagE></tagD></tagA>
这是
很
易读
这更难读
查看
更新:这里是MSDN上的一个好链接
此外,以下是一个示例:
class Program
{
static void Main(string[] args)
{
var Mark = new Person()
{
Name = "Mark",
Email = "mark@example.com"
};
var serializer = new DataContractSerializer(typeof(Person));
var settings = new XmlWriterSettings()
{
Indent = true,
IndentChars = "\t"
};
using (var writer = XmlWriter.Create(Console.Out, settings))
{
serializer.WriteObject(writer, Mark);
}
Console.ReadLine();
}
}
public class Person
{
public string Name { get; set; }
public string Email { get; set; }
}
正如bendewey所说,XmlWriterSettings是您所需要的—例如
var ds = new DataContractSerializer(typeof(Foo));
var settings = new XmlWriterSettings { Indent = true };
using (var w = XmlWriter.Create("fooOutput.xml", settings))
ds.WriteObject(w, someFoos);
公共静态字符串序列化实体(T源)
{
使用(MemoryStream ms=new MemoryStream())
{
NetDataContractSerializer=新的NetDataContractSerializer();
serializer.Serialize(ms,source);
返回System.Text.Encoding.ASCII.GetString(ms.ToArray());
}
}
公共静态T反序列化实体(字符串xml)
{
使用(MemoryStream ms=new MemoryStream(System.Text.Encoding.ASCII.GetBytes(xml)))
{
NetDataContractSerializer=新的NetDataContractSerializer();
返回(T)序列化程序。反序列化(ms);
}
}
在调整XML文档中的空格时要小心!调整空白将使XML对我们人类更具可读性,但它可能会干扰机器解析
根据,默认情况下空白是重要的。换句话说,就XML而言,空白就是内容
如果将格式良好的XML输入到XML文档对象中,将得到与没有空格或换行符的版本不同的结果。您将在已格式化的版本中添加其他文本节点
这篇关于MSDN的文章有几个例子可以说明空白是多么棘手
如果您只为人类使用而格式化XML,那没关系。但如果您试图对格式化文档进行往返,可能会遇到麻烦
由于使用DataContractSerializer的主要好处之一是能够无缝地序列化对象和反序列化XML,因此通常最好不要处理丑陋的输出
我通常会将输出粘贴到NotePad++中,并在需要进行调试时在其上运行一个XML TITY宏。根据此处发布的其他使用XmlWriter的示例,这里有一个版本(from),可用于streams(以及特定的Ionic.Zip库),还显示了不应用格式时的代码(使用条件编译-只需注释掉#define即可使其编写无格式的XML)
这有点延迟,但我在我的帖子中添加了一个更新。这不是UTF8,不是ASCII吗?记事本的快捷方式++一个XML整洁的宏查看出现在“外部”元素的空白不是明显的空白;根据内容模型(例如,元素与混合内容),它会变得棘手,并且可以肯定元素或属性中的空白是重要的,因此没有多行元素内容的缩进!我发现
DataContractSerializer
对自己创建的“缩进”文档进行反序列化没有问题。
public static string SerializeEntity<T>(T source)
{
using (MemoryStream ms = new MemoryStream())
{
NetDataContractSerializer serializer = new NetDataContractSerializer();
serializer.Serialize(ms, source);
return System.Text.Encoding.ASCII.GetString(ms.ToArray());
}
}
public static T DeSerializeEntity<T>(string xml)
{
using (MemoryStream ms = new MemoryStream(System.Text.Encoding.ASCII.GetBytes(xml)))
{
NetDataContractSerializer serializer = new NetDataContractSerializer();
return (T)serializer.Deserialize(ms);
}
}
#define WRITE_FORMATTED_XML
using System.Xml;
namespace ClipFlair.Windows
{
public partial class BaseWindow : FloatingWindow
{
//...
#if WRITE_FORMATTED_XML
private static XmlWriterSettings XML_WRITER_SETTINGS = new XmlWriterSettings() { Indent=true, IndentChars=" "};
#endif
//...
public virtual void SaveOptions(ZipFile zip, string zipFolder = "") //THIS IS THE CORE SAVING LOGIC
{
if (SavingOptions != null) SavingOptions(this, null); //notify any listeners
View.Busy = true;
try
{
ZipEntry optionsXML = zip.AddEntry(zipFolder + "/" + View.GetType().FullName + ".options.xml",
new WriteDelegate((entryName, stream) =>
{
DataContractSerializer serializer = new DataContractSerializer(View.GetType()); //assuming current View isn't null
#if WRITE_FORMATTED_XML
using (XmlWriter writer = XmlWriter.Create(stream, XML_WRITER_SETTINGS))
serializer.WriteObject(writer, View);
#else
serializer.WriteObject(stream, View);
#endif
}));
}
catch (Exception e)
{
MessageBox.Show("ClipFlair options save failed: " + e.Message); //TODO: find the parent window
}
finally
{
View.Busy = false; //in any case (error or not) clear the Busy flag
}
if (SavedOptions != null) SavedOptions(this, null); //notify any listeners
}
//...
}
}