如何在具有特定名称的当前程序集中查找 C# 接口的实现?

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/19656/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me): StackOverFlow

提示:将鼠标放在中文语句上可以显示对应的英文。显示中英文
时间:2020-08-01 09:03:25  来源:igfitidea点击:

How to find an implementation of a C# interface in the current assembly with a specific name?

提问by Daren Thomas

I have an Interface called IStepthat can do some computation (See "Execution in the Kingdom of Nouns"). At runtime, I want to select the appropriate implementation by class name.

我有一个接口IStep,可以进行一些计算(请参阅“名词王国中的执行”)。在运行时,我想通过类名选择适当的实现。

// use like this:
IStep step = GetStep(sName);

采纳答案by lubos hasko

Your question is very confusing...

你的问题好纠结。。。

If you want to find types that implement IStep, then do this:

如果要查找实现 IStep 的类型,请执行以下操作:

foreach (Type t in Assembly.GetCallingAssembly().GetTypes())
{
  if (!typeof(IStep).IsAssignableFrom(t)) continue;
  Console.WriteLine(t.FullName + " implements " + typeof(IStep).FullName);
}

If you know already the name of the required type, just do this

如果您已经知道所需类型的名称,请执行此操作

IStep step = (IStep)Activator.CreateInstance(Type.GetType("MyNamespace.MyType"));

回答by Ian Nelson

If the implementation has a parameterless constructor, you can do this using the System.Activator class. You will need to specify the assembly name in addition to the class name:

如果实现具有无参数构造函数,则可以使用 System.Activator 类来执行此操作。除了类名之外,您还需要指定程序集名称:

IStep step = System.Activator.CreateInstance(sAssemblyName, sClassName).Unwrap() as IStep;

http://msdn.microsoft.com/en-us/library/system.activator.createinstance.aspx

http://msdn.microsoft.com/en-us/library/system.activator.createinstance.aspx

回答by Daren Thomas

Based on what others have pointed out, this is what I ended up writing:

根据其他人所指出的,这就是我最终写的:

/// 
/// Some magic happens here: Find the correct action to take, by reflecting on types 
/// subclassed from IStep with that name.
/// 
private IStep GetStep(string sName)
{
    Assembly assembly = Assembly.GetAssembly(typeof (IStep));

    try
    {
        return (IStep) (from t in assembly.GetTypes()
                        where t.Name == sName && t.GetInterface("IStep") != null
                        select t
                        ).First().GetConstructor(new Type[] {}
                        ).Invoke(new object[] {});
    }
    catch (InvalidOperationException e)
    {
        throw new ArgumentException("Action not supported: " + sName, e);
    }
}

回答by samjudson

Well Assembly.CreateInstance would seem to be the way to go - the only problem with this is that it needs the fully qualified name of the type, i.e. including the namespace.

那么 Assembly.CreateInstance 似乎是要走的路 - 唯一的问题是它需要类型的完全限定名称,即包括命名空间。