使用反射,我如何能得到所有类型的实现接口与c# 3.0/。NET 3.5用最少的代码,最小化迭代?

这是我想重写的内容:

foreach (Type t in this.GetType().Assembly.GetTypes())
    if (t is IMyInterface)
        ; //do stuff

当前回答

OfType Linq方法正好可以用于这种场景:

https://learn.microsoft.com/fr-fr/dotnet/api/system.linq.enumerable.oftype?view=netframework-4.8

其他回答

遍历所有加载的程序集,遍历它们的所有类型,并检查它们是否实现了接口。

喜欢的东西:

Type ti = typeof(IYourInterface);
foreach (Assembly asm in AppDomain.CurrentDomain.GetAssemblies()) {
    foreach (Type t in asm.GetTypes()) {
        if (ti.IsAssignableFrom(t)) {
            // here's your type in t
        }
    }
}

我的是c# 3.0:)

var type = typeof(IMyInterface);
var types = AppDomain.CurrentDomain.GetAssemblies()
    .SelectMany(s => s.GetTypes())
    .Where(p => type.IsAssignableFrom(p));

基本上,最少的迭代次数总是:

loop assemblies  
 loop types  
  see if implemented.

如果它能帮助任何人,这是我正在使用的使我的一些单元测试更容易:)

public static Type GetInterfacesImplementation(this Type type)
{
    return type.Assembly.GetTypes()
        .Where(p => type.IsAssignableFrom(p) && !p.IsInterface)
        .SingleOrDefault();
}

其他答案是没有使用通用接口。

这一个做到了,只是用typeof(T)替换typeof(ISomeInterface)。

List<string> types = AppDomain.CurrentDomain.GetAssemblies().SelectMany(x => x.GetTypes())
            .Where(x => typeof(ISomeInterface).IsAssignableFrom(x) && !x.IsInterface && !x.IsAbstract)
            .Select(x => x.Name).ToList();

所以,

AppDomain.CurrentDomain.GetAssemblies().SelectMany(x => x.GetTypes())

我们得到了所有的集合

!x.IsInterface && !x.IsAbstract

是用来排除接口和抽象的和

.Select(x => x.Name).ToList();

把它们列在一个列表里。

我在这里看到了太多过于复杂的答案,人们总是告诉我,我倾向于把事情复杂化。同样使用IsAssignableFrom方法来解决OP问题也是错误的!

下面是我的例子,它从应用程序域中选择所有程序集,然后它采用所有可用类型的平面列表,并检查每个类型的接口列表是否匹配:

public static IEnumerable<Type> GetImplementingTypes(this Type itype) 
    => AppDomain.CurrentDomain.GetAssemblies().SelectMany(s => s.GetTypes())
           .Where(t => t.GetInterfaces().Contains(itype));