检查程序集中的类是否包含接口中的所有方法

时间:2012-02-21 13:03:26

标签: c# reflection

我有在运行时加载的自定义程序集。

此时我有加载dll的代码,可以创建对象andexecute方法的新实例。

如何验证该类是否实现了我在接口中定义的所有函数。

(我正在尝试使用可在运行时切换的不同操作创建插件系统,以提供不同的行为)。

我的代码就像这是主程序:

public Interface IArticleManager{
 void SetMenuId(int MenuId);
 void SetMenu(string name);
 void SetContent(string content);
 bool Save();
}

我的类库(断开连接,你可以从解决方案中看到它)

public class XmlArticle{
    public void SetMenuId(int MenuId){
       //some implementation
     }
     public void SetMenu(string name){
       //some implementation
}
     public void SetContent(string content){
       //some implementation
}
    public bool Save(){
}
}


public class SqlArticle{
    public void SetMenuId(int MenuId){
       //some implementation
     }
     public void SetMenu(string name){
       //some implementation
}
     public void SetContent(string content){
       //some implementation
}
    public bool Save(){
}
}

4 个答案:

答案 0 :(得分:3)

基本上,要改写一下,你想检查一个类是否定义了一个接口的契约,即使它没有明确地实现那个接口?

这非常非常重要,而且非常非常糟糕。相反,我强烈建议您将插件接口重构为合同程序集,并从插件和主应用程序引用程序集。然后,您的插件实际上可以实现合同,并且您可以避免编译器保护,从而搞乱实现。

但是,如果你坚持沿着这条路走下去,那么:

var interfaceType = typeof(IArticleManager);
var targetType = typeof(SqlArticle);
foreach(var member in interfaceType.GetMembers())
{
    var targetMember = targetType.GetMember(member.Name);
    // compare the arguments, generic constraints, etc here
}

我会留给你做比较,因为它老实说是大量的编码。您需要检查该成员是属性,事件或方法,通用或非通用等。

答案 1 :(得分:1)

检查一个类实现接口中的所有方法是没有用的,除非它实际实现了接口本身 - 事实上它具有相同的方法名称最终只是巧合。

要检查对象实例是否实现了接口:

if (obj is IArticleManager)

将返回true。

但是,如果你想实际使用界面的方法,那就更好(少投射):

IArticleManager manager = obj as IArticleManager;  
if (manager != null)  
{ do stuff }

答案 2 :(得分:1)

看起来你需要做的就是将接口移动到一个单独的程序集中,该程序集只包含“主程序”和动态加载的DLL都可以访问的接口。

因此,为了创建动态加载的DLL并期望它在您的基础结构中工作,作者首先需要引用接口程序集,然后实现提供的接口。

答案 3 :(得分:0)

IArticleManager当你不能在任何地方使用它时,目的是什么?

除此之外,如果我们接受你想制作一个非常松散的插件系统,你可以强制要求每个插件程序集只有一个公共类,然后通过反射实例化该类,并通过反射调出它的方法,同时传递适当的参数。

与每个插件或其他外部代码一样,您应该验证输出并保护您的应用程序免受错误(即捕获并记录插件异常)。这也可以处理无效的插件(没有所需签名的插件)