动态在 c# 中没有 IDynamicMetaObject
本文关键字:IDynamicMetaObject 动态 | 更新日期: 2023-09-27 18:33:14
对象可以通过实现来提供其绑定语义 IDynamicMetaObject 提供程序 — 或者通过子类化更容易 DynamicObject,它提供了此的默认实现 接口。
源
我从未实现过这个接口或类,并且总是能够动态执行事情:
public class aa
{
public void bbb()
{ }
}
dynamic a = new aa().bbb();
那么他们这句话是什么意思呢?
我试图了解何时需要使用IDynamicMetaObject或DynamicObject继承
dynamic
关键字会导致对对象的引用被后期绑定,并且仅在运行时解析。通常,这样做的原因是您使用的是IDynamicMetaObjectProvider
实现器,它允许您的代码决定如何处理运行时属性解析。也就是说,您可能希望在运行时添加和删除属性(通常作为字典实现,如 ExpandoObject
(。
您的示例代码所做的只是阻止编译类型类型检查。事实上,这比什么都不做更糟糕,因为如果您编写的代码访问了类中不存在的属性或方法,它仍然可以编译,但当然会在运行时崩溃。我想不出很多很好的理由来引用带有dynamic
的具体类(期望软弱的类型转换或鸭子类型,但我们通常在 C# 中使用接口来处理这样的东西!
我自己的一个项目继承DynamicObject
的动态对象的实现示例:
https://github.com/jamietre/IQObjectMapper/blob/master/source/IQObjectMapper/IQDynamicObject.cs
(它调用一个工厂方法,该方法返回一个带有选项的新字典,您需要做的就是将构造函数从:
InnerDict = ObjectMapper.MapperCache.GetDictionary<object>(Options);
自:
InnerDict = new Dictionary<string,object>();
并摆脱几个检查选项的条件
我讨厌给出这样的"精辟"答案,因为它的信息量不是很大,但这确实是一个"如果你需要它,你会知道"的情况。
很少需要在应用程序中实现动态对象,甚至是大多数库代码。该接口适用于实现只能用作动态对象的类的人;例如,如果你想在你的对象上实现类似Javascript的行为。您可以在此类对象上调用所需的任何属性或方法,它将进行编译。由运行时的实现来确定给定调用是否有效。
一个完全没有意义但描述性的示例是一个类,它根据星期几决定哪些属性有效:
public class WeekendObject : DynamicObject
{
Dictionary<string, object> propertybag = new Dictionary<string, object>();
public override bool TryGetMember(GetMemberBinder binder, out object result)
{
if (DateTime.Now.DayOfWeek == DayOfWeek.Sunday)
{
if (name.StartsWith("Sunday"))
{
return propertybag.TryGetValue(name, out result);
}
}
else
{
if (!name.StartsWith("Sunday"))
{
return propertybag.TryGetValue(name, out result);
}
}
}
public override bool TrySetMember(SetMemberBinder binder, object value)
{
if (DateTime.Now.DayOfWeek == DayOfWeek.Sunday)
{
if (name.StartsWith("Sunday"))
{
propertybag[binder.Name.ToLower()] = value;
return true;
}
}
else
{
if (!name.StartsWith("Sunday"))
{
propertybag[binder.Name.ToLower()] = value;
return true;
}
}
return false;
}
}