您好我有一个包含很多类的命名空间,并且所有类都有一个方法Destroy(int id) 我想用动态词来调用该方法。
以下是我的例子:
public bool DeleteElement<T>(T tElement)
{
Type t = typeof(T);
dynamic element = tElement;
var id = element.Id;
//until here everything is fine
//here I want to say
(namespace).myClassName.Destroy(id);
//the name of myClassName is like t.ToString()
}
我可以避免命名空间,包括在顶部使用。我的想法是使用动态调用静态方法,而不是反射,请看Destroy是T的静态方法。我需要这样的东西T.Destroy(id)
答案 0 :(得分:5)
如果Destroy(int id)
是一个静态方法,你不能创建一个可以调用静态方法的实例方法吗?
public void Destroy()
{
ThisClass.Destroy(this.Id);
}
然后,您可以定义由所有这些类实现的IDestroyable
接口:
interface IDestroyable { void Destroy(); }
然后按如下方式修改DeleteElement
方法:
public bool DeleteElement<T>(T tElement) where T : IDestroyable
{
tElement.Destroy();
}
此处无需使用dynamic
......实际上,在这种情况下使用dynamic
通常表明设计不当。实际上需要 dynamic
是非常罕见的,除非在创建它的场景中(例如,使用动态语言互操作)
(如果已生成类但它们具有partial
修饰符,则可以在另一个未被生成器触及的文件中声明新方法)
编辑:如果类是生成的而不是partial
,则无法修改它们......所以另一种解决方案是使用反射;我知道你想避免这种情况(出于性能原因,我假设),但你可以通过对每种类型只进行一次反射来限制性能影响:你只需要为每种类型创建和缓存一个委托。
class DestroyHelper<T>
{
static readonly Action<int> _destroy;
static readonly Func<T, int> _getId;
static DestroyHelper()
{
var destroyMethod = typeof(T).GetMethod("Destroy", BindingFlags.Static | BindingFlags.Public);
_destroy = (Action<int>)Delegate.CreateDelegate(typeof(Action<int>), destroyMethod);
var getIdMethod = typeof(T).GetProperty("Id").GetGetMethod();
_getId = (Func<T, int>)Delegate.CreateDelegate(typeof(Func<T, int>), getIdMethod);
}
public static void Destroy(T element)
{
_destroy(_getId(element));
}
}