c# - 只获取直接接口(interface)而不是全部?

标签 c# reflection

我有一个像下面这样的类。 GetInterfaces() 说

If the current Type represents a type parameter in the definition of a generic type or generic method, this method searches the interface constraints and any interfaces inherited from class or interface constraints.

我有可能得不到任何继承的接口(interface)吗?当我在 ABC 上使用 GetInterfaces 时,我只想看到 DEF,而不是 DEF 和 GHI。

interface DEF : GHI {...}
class ABC : DEF {...}

最佳答案

首先,您发布的 MSDN 片段与您的实际问题没有任何关系。例如,当您拥有诸如 class Foo<T> where T : IEnumerable 之类的通用类型时,它会处理。 ,然后您尝试调用 GetInterfaces在类型参数上 T ,例如通过 typeof(Foo<>).GetGenericArguments().Single().GetInterfaces().

其次,这个问题有点不明确。请注意,当一个类实现接口(interface)时,它必须实现所有 由该接口(interface)“继承”的接口(interface)。它只是一个 C# 便利功能,可让您在类声明中省略继承的接口(interface)。在您的示例中,明确包含“继承的”GHI 是完全合法的(并且没有什么不同)接口(interface):

class ABC : DEF, GHI {...}

我假设您真正想要做的是找到一个“最小的”接口(interface)集,它“涵盖”该类型的所有已实现接口(interface)。这导致了一个稍微简化的版本 Set cover problem .

这是解决它的一种方法,无需任何尝试以提高算法效率。这个想法是通过过滤掉由该类型实现的其他接口(interface)已经实现的那些接口(interface)来生成最小接口(interface)集。

Type type = ...

var allInterfaces = type.GetInterfaces();    
var minimalInterfaces = from iType in allInterfaces 
                        where !allInterfaces.Any(t => t.GetInterfaces()
                                                       .Contains(iType))
                        select iType;

( 编辑 - 这是执行上述操作的更好方法:

var minimalInterfaces = allInterfaces.Except
                        (allInterfaces.SelectMany(t => t.GetInterfaces()));

)

例如,对于 List<int> :

allInterfaces: 

System.Collections.Generic.IList`1[System.Int32]
System.Collections.Generic.ICollection`1[System.Int32]
System.Collections.Generic.IEnumerable`1[System.Int32]
System.Collections.IEnumerable
System.Collections.IList
System.Collections.ICollection

minimalInterfaces:

System.Collections.Generic.IList`1[System.Int32]
System.Collections.IList

请注意,此解决方案仅涵盖接口(interface)“层次结构”(这是您看起来想要的),而不是它们与类的 层次结构的关系。特别是,它不会关注接口(interface)首先在类的层次结构中何处实现。

例如,假设我们有:

interface IFoo { }
interface IBar : IFoo { }
interface IBaz { } 

class Base : IBar {  }
class Derived : Base, IBaz {  }

现在,如果您尝试使用我描述的解决方案来获得 Derived 的最小接口(interface)集,你会得到 IBaz以及IBar .如果你不想IBar ,您将不得不付出更多努力:消除由基类实现的接口(interface)。最简单的方法是从最小接口(interface)集中删除由该类的直接基类实现的那些接口(interface),如@MikeEast 的回答中所述。

关于c# - 只获取直接接口(interface)而不是全部?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/5318685/

相关文章:

reflection - Kotlin - 获取 KProperty1<T, out R> 的属性类型

c# - Entity Framework 连接字符串 "The Server was not found"

javascript - 如何停止 Razors 自动编码\n?

c# - 如何在属性网格中加载 xml 文档

scala - 为什么 Scala 方法 isInstanceOf[T] 不起作用

c# - 使用反射获取变量名

c# - 查找不[可序列化]的项目

c# - 将日期从 json 转换为日期时间

c# - 代码后面的 specflow 有语法错误或重复代码

java - 如何获取类及其父类(super class)的注释列表