我正在阅读Adam Nathan的书“WPF 4 Unleashed”,第82页有以下警告:
在XAML中设置依赖项属性时,在运行时绕过.NET属性包装器!
虽然XAML编译器依赖于 在编译时,属性包装器,WPF调用底层 GetValue和SetValue方法直接在运行时!因此,到 在XAML中设置属性和程序之间保持奇偶校验 代码,属性包装器中不包含任何逻辑至关重要 除了GetValue / SetValue调用。如果要添加自定义 逻辑,这就是注册回调的用途。所有的WPF 内置属性包装器遵守此规则,因此此警告适用于 任何人编写具有自己的依赖属性的自定义类。
我的问题是:为什么? WPF调用GetValue()/ SetValue()而不是读取/设置CLR属性包装器的原因是什么?如果原因是读取/设置属性包装器需要反射,那么无论如何WPF在构造对象树时都会使用反射,那么绕过使用属性包装并直接调用GetValue()/ SetValue()是否真的值得呢?或者避免反思不是这种行为的主要原因吗?
UPD。 Clemens迅速给出了正确答案,但我会在MSDN页面中再添加一个引用(据我所知,StackOverflow更喜欢引用链接):
通过xmlns和assembly的组合查找类型 属性,但识别成员,确定哪些可以 支持被设置为属性,并解析什么类型的 否则,财产价值支持需要广泛反思 使用PropertyInfo。因为给定类型的依赖属性是 通过属性系统WPF可以作为存储表访问 其XAML处理器的实现使用此表并推断出 通过调用SetValue可以更有效地设置任何给定属性ABC 在包含DependencyObject派生类型上,使用依赖项 属性标识符ABCProperty。
答案 0 :(得分:3)
XAML Loading and Dependency Properties中给出了解释:
其XAML处理器的当前WPF实现本质上是 依赖属性意识到。 WPF XAML处理器使用属性系统 加载二进制XAML和时的依赖属性的方法 处理属性是依赖属性。这有效 绕过属性包装器。实现自定义依赖项时 属性,你必须考虑到这种行为,应该避免 将任何其他代码放在属性包装器中除了 属性系统方法GetValue和SetValue。
和
出于实施原因,它在计算上更便宜 将属性标识为依赖属性并访问该属性 系统SetValue方法设置它,而不是使用属性 包装器及其二传手。这是因为XAML处理器必须推断 支持代码的整个对象模型仅基于知道 由结构表示的类型和成员关系 标记和各种字符串。