Mono.Cecil type.IsAssignableFrom(derivedType)等价物

时间:2011-04-15 10:22:39

标签: c# reflection inheritance cil mono.cecil

我正在使用Mono.Cecil在Assembly中查找派生类型的类型。 Normaly可以使用IsAssignableFrom()方法完成,但我不能在Cecil中使用它。 有没有这样的方法或其他方法来检查它? 谢谢 麦克

4 个答案:

答案 0 :(得分:4)

继承检查和“赋值兼容性”检查实际上是不同的事情。您想检查继承还是“赋值兼容性”?

分配兼容性包括很多内容,包括签名/未签名转换,基本类型转换枚举,charshort转换,通用差异转换,从接口到object的转换,从数组到IListIList<T>及其基接口,数组协方差,通用参数到约束,以及一大堆其他东西。

您最好的选择是在ECMA规范中查找分配兼容性和“验证类型兼容性”规则以获取完整列表。

我猜你的特殊需求,你会想要完整的“分配兼容性检查”的一些子集。

不幸的是,Cecil没有任何方法可以为您实现这一点,但它确实为您提供了足够的信息来实现这一点。

使用cecil实现类似的功能时需要小心。特别是TypeReference类有一个“Resolve”方法,在某些情况下你需要调用它(用于查找未解析类型引用的TypeDefinition),但是在其他情况下你不能调用它,因为它会在类型树。您还需要处理“结构类型相等”以比较通用瞬时,并且在处理类型层次结构时必须处理通用参数替换。

答案 1 :(得分:2)

我从来没有对Mono做过任何事情,更不用说Cecil了,但是通过GitHub来源,我猜你可能会对这个类型的TypeDefinition做一些事情:

public bool HasInterface(TypeDefinition type, string interfaceFullName)
{
  return (type.Interfaces.Any(i => i.FullName.Equals(interfaceFullName)) 
          || type.NestedTypes.Any(t => HasInterface(t, interfaceFullName)));
}

答案 2 :(得分:1)

查找类型为AType的派生类型的一种方法是枚举程序集中定义的所有类型,并将它们的BaseType属性与AType类型进行比较。此方法在ILSpy中用于显示所选类型的派生类型。实现在FindDerivedTypes方法(DerivedTypesTreeNode.cs)中。要查找间接派生的类型,必须迭代BaseType属性(使用Resolve()),直到达到AType或BaseType等于null。

答案 3 :(得分:0)

ApiChange工具确实使用Mono Cecil。它可以找到使用类型的所有出现,包括使用命令

从类型派生
  

ApiChange.exe -whousestype   “CommandBase”ApiChange.Api.dll -in   ApiChange.Api.dll -excel

您将获得包含您所有类型用户的文件和行号的Excel输出。它看起来像

ApiChange.Api.dll   internal class ApiChange.Api.Scripting.CorFlagsCommand          Inherits from   internal class ApiChange.Api.Scripting.CommandBase  C:\Source\ApiChangeTooling\ApiChange.Api\src\Scripting\Commands\CorFlagsCommand.cs  
ApiChange.Api.dll   internal class ApiChange.Api.Scripting.WhoImplementsInterfaceCommand            Inherits from   internal class ApiChange.Api.Scripting.CommandBase  C:\Source\ApiChangeTooling\ApiChange.Api\src\Scripting\Commands\WhoImplementsInterfaceCommand.cs    
ApiChange.Api.dll   internal class ApiChange.Api.Scripting.DiffAssembliesCommand            Inherits from   internal class ApiChange.Api.Scripting.CommandBase  C:\Source\ApiChangeTooling\ApiChange.Api\src\Scripting\Commands\DiffAssembliesCommand.cs    

使用Cecil的实际代码位于WhoUsesType.cs

此致,   Alois Kraus