我有一个像
这样的课程 [Serializable]
public class MyClass
{
[XmlAttribute]
public bool myBool { get; set; }
}
但是当xml中不存在该属性时,这会将bool的值序列化为false。 当属性不在xml中时,我希望该属性为null。
所以我试过这个
[Serializable]
public class MyClass
{
[XmlAttribute]
public bool? myBool { get; set; }
}
然后是序列化器错误
Type t = Type.GetType("Assembly.NameSpace.MyClass");
XmlSerializer mySerializer = new XmlSerializer(t); //error "There was an error reflecting type"
请举个例子说明我能做到这一点。我知道在SO上有一些相关的问题,但没有任何东西能说明如何用可空的bool来克服反射误差。感谢。
答案 0 :(得分:10)
您需要使用“* Specified”字段模式来控制它(请参阅MSDN上的“控制生成的XML”):
[Serializable]
public class MyClass
{
[XmlAttribute]
public bool myBool { get; set; }
[XmlIgnore]
public bool myBoolSpecified;
}
逻辑现在变为:
!myBoolSpecified
,则myBool
逻辑null
true
false
或myBool
答案 1 :(得分:3)
有关处理可空字段和XML属性的信息,请查看this。这里也有类似的question。基本上,序列化程序无法处理定义为可为空的XML属性字段,但有一种解决方法。
即2个属性,一个包含可空(不是XML存储),另一个用于读/写(XML属性存储为字符串)。也许这可能就是你所需要的?
private bool? _myBool;
[XmlIgnore]
public bool? MyBool
{
get
{
return _myBool;
}
set
{
_myBool = value;
}
}
[XmlAttribute("MyBool")]
public string MyBoolstring
{
get
{
return MyBool.HasValue
? XmlConvert.ToString(MyBool.Value)
: string.Empty;
}
set
{
MyBool =
!string.IsNullOrEmpty(value)
? XmlConvert.ToBoolean(value)
: (bool?)null;
}
}
答案 2 :(得分:2)
您可以使用 XmlElementAttribute.IsNullable :
[Serializable]
public class MyClass
{
[XmlElement(IsNullable = true)]
public bool? myBool { get; set; }
}
答案 3 :(得分:1)
问题是可空类型必须定义为元素(默认)而不是属性。
原因是当值为null时,它可以表示为<mybool xs:nil="true"/>
,因为不能表示为属性。
看一下这个片段:
[Serializable]
public class MyClass
{
// removed the attribute!!!
public bool? myBool { get; set; }
}
和
XmlSerializer serializer = new XmlSerializer(typeof(MyClass));
var stream = new MemoryStream();
serializer.Serialize(stream, new MyClass(){myBool = null});
Console.WriteLine(Encoding.UTF8.GetString(stream.ToArray()));
输出:
<?xml version="1.0"?>
<MyClass xmlns:xsd="http://www.w3.org/2001/XMLSchema" xmlns:xsi="http://www.w3.o
rg/2001/XMLSchema-instance">
<myBool xsi:nil="true" /> <!-- NOTE HERE !!! -->
</MyClass>