I have a class which is used for Xml Serialization.
Inside which I have a nullable property which is decorated with XmlAttribute:
[XmlAttribute(\"la
I know this topic is old. This is the solution I came with. A class which encapsulates the type, and has implicit casting to the type. When serializing, the member variable can be marked with IsNullable = false without getting compiler errors, and blocking it from being serialized when null.
public class Optional<T> where T : struct, IComparable
{
public Optional(T valueObject)
{
Value = valueObject;
}
public Optional()
{
}
[XmlText]
public T Value { get; set; }
public static implicit operator T(Optional<T> objectToCast)
{
return objectToCast.Value;
}
public static implicit operator Optional<T>(T objectToCast)
{
return new Optional<T>(objectToCast);
}
}
Then use it in your class
[Serializable]
[XmlRoot(ElementName = "foo")]
public class foo
{
[XmlElement(ElementName = "myInteger", isNullable = false)]
Optional<int> myInt;
}
You can do things like
myFoo.myInt = 7;
int j = 8 + myFoo.myInt;
For all purposes it's an int. For serialization purposes, it can be null and blocked from being serialized.
Nullable is not directly supported by XmlSerialization.
If you want use a nullable property you must use a non nullable property and add a boolean property with the same name of property with the suffix "Specified" which specifie when the property must be serializable.
An example with your case :
private DateTime? _lastUpdated;
[XmlAttribute("lastUpdated")]
public DateTime LastUpdated {
get {
return (DateTime)_lastUpdated;
}
set
{
_lastUpdated = value;
}
}
public bool LastUpdatedSpecified
{
get
{
return _lastUpdated.HasValue;
}
}
You can use XmlElementAttribute.IsNullable:
[Serializable]
public class Result
{
[XmlElement(IsNullable = true)]
public DateTime? LastUpdated { get; set; }
}
Note: This works for sure in SOAP contracts in WCF. I haven't tested in other Xml serialization scenarios.
When using a [DataContract]
you can use
[DataMember(EmitDefaultValue = false)]
boolean
it will only emit the value if it is true
.nullable boolean
it will only emit if it is not null
.string
it will only emit the value if it isn't null
.int
it will only emit the value if it isn't 0
.etc.
Make sure to put [DataContract]
on the class itself and [DataMember]
on all members you want serialized, whether you're specifying EmitDefaultValue
or not.
Setting the EmitDefaultValue property to false is not a recommended practice. It should only be done if there is a specific need to do so (such as for interoperability or to reduce data size).
https://msdn.microsoft.com/en-us/library/system.runtime.serialization.datamemberattribute.emitdefaultvalue(v=vs.110).aspx
This is working for me.
[XmlIgnore]
public float? Speed { get; set; }
[XmlAttribute("Speed")]
public float SpeedSerializable
{
get
{
return this.Speed.Value;
}
set { this.Speed = value; }
}
public bool ShouldSerializeSpeedSerializable()
{
return Speed.HasValue;
}