I am using the new .NET 3.0 DataContractSerializer. I have both Nullable<> and List<> objects I am going to serialize. Example:
我正在使用新的.NET 3.0 DataContractSerializer。我有Nullable <>和List <>对象我要序列化。例:
[DataContract(Namespace = "")]
class Test
{
public static void Go()
{
Test test = new Test();
var dcs = new DataContractSerializer(typeof(Test));
dcs.WriteObject(new StreamWriter("test.xml").BaseStream, test);
}
[DataMember]
public Nullable<int> NullableNumber = null;
[DataMember]
public int Number = 5;
[DataMember]
public List<int> Numbers = new List<int>();
}
When .NET serializes a null or an empty list, it puts in nil (for Nullable) and empty (for lists) elements into the XML. The above example generates:
当.NET序列化空列表或空列表时,它将nil(对于Nullable)和空(对于列表)元素放入XML中。以上示例生成:
<Test xmlns:i="http://www.w3.org/2001/XMLSchema-instance">
<NullableNumber i:nil="true"/>
<Number>5</Number>
<Numbers xmlns:a="http://schemas.microsoft.com/2003/10/Serialization/Arrays"/>
</Test>
For reasons I don't have time to describe I would like to eliminate the superfluous NullableNumber and Numbers elements, like so:
由于我没有时间描述的原因,我想消除多余的NullableNumber和Numbers元素,如下所示:
<Test xmlns:i="http://www.w3.org/2001/XMLSchema-instance">
<Number>5</Number>
</Test>
Indeed, the above file deserializes with the serializer just fine.
实际上,上面的文件反序列化了串行器就好了。
Thanks for your help!
谢谢你的帮助!
2 个解决方案
#1
24
Mark the field with
标记该字段
[DataMember(EmitDefaultValue=false)]
That will work for at the least the nullable value type case. For the List case you may need to defer creation of the list until it is needed, or else null the member if it is empty before serialization.
这将至少适用于可空值类型的情况。对于List情况,您可能需要在需要时推迟创建列表,否则如果成员在序列化之前为空,则为null。
#2
1
I really needed the same thing, but applied globally to lots of fields in generated RIA classes. I'm not sure if this XML is acceptable to DataConstract for deserializing. But it is readable, which suites my purposes...
我真的需要相同的东西,但全局应用于生成的RIA类中的许多字段。我不确定这个XML是否可以被DataConstract接受用于反序列化。但它是可读的,符合我的目的......
public override string ToString()
{
var doc = XDocument.Parse(this.ToXML());
WalkElement(doc.Root);
return doc.ToString( SaveOptions.None );
}
void WalkElement(XElement e)
{
var n = e.GetNamespaceOfPrefix("i");
if (n != null)
{
var a = e.Attribute(n + "nil");
if (a != null && a.Value.ToLower() == "true")
e.Remove();
}
foreach (XElement child in e.Elements().ToList())
WalkElement(child);
}
#1
24
Mark the field with
标记该字段
[DataMember(EmitDefaultValue=false)]
That will work for at the least the nullable value type case. For the List case you may need to defer creation of the list until it is needed, or else null the member if it is empty before serialization.
这将至少适用于可空值类型的情况。对于List情况,您可能需要在需要时推迟创建列表,否则如果成员在序列化之前为空,则为null。
#2
1
I really needed the same thing, but applied globally to lots of fields in generated RIA classes. I'm not sure if this XML is acceptable to DataConstract for deserializing. But it is readable, which suites my purposes...
我真的需要相同的东西,但全局应用于生成的RIA类中的许多字段。我不确定这个XML是否可以被DataConstract接受用于反序列化。但它是可读的,符合我的目的......
public override string ToString()
{
var doc = XDocument.Parse(this.ToXML());
WalkElement(doc.Root);
return doc.ToString( SaveOptions.None );
}
void WalkElement(XElement e)
{
var n = e.GetNamespaceOfPrefix("i");
if (n != null)
{
var a = e.Attribute(n + "nil");
if (a != null && a.Value.ToLower() == "true")
e.Remove();
}
foreach (XElement child in e.Elements().ToList())
WalkElement(child);
}