如何使用C#中的reflection查找实现generics抽象类的所有类?
我有一个看起来像这样的c#
类
public abstract class Listener where T : Event { public abstract void Handle(T _event); }
我把这个类延伸到这个类
public class SendWelcomeEmail : Listener { public override void Handle(UserWasCreated _event) { //... } }
我需要使用reflection来查找扩展Listener
基类的所有类。
我尝试了以下内容
var listeners = AppDomain.CurrentDomain.GetAssemblies() .SelectMany(assembly => assembly.GetTypes()) .Where(x => x.IsClass && !x.IsInterface) .Where(listener => !listener.IsAbstract && listener.IsGenericType && listener.GetGenericTypeDefinition() == typeof(Listener)) .ToList();
但这并不会带来任何回报。 这个条件一直返回false listener.GetGenericTypeDefinition() == typeof(Listener)
如何才能正确找到扩展Listener
基类的所有类?
首先构建您需要的基础架构:在工具箱中放置更多工具,然后使用这些工具。
您想列出类型的所有基类型,因此列出类型的所有基类型:
static class Extensions { public static IEnumerable BaseTypes(this Type type) { Type t = type; while (true) { t = t.BaseType; if (t == null) break; yield return t; } } }
现在我们的工具箱中有一个有用的工具。
我们有一个类型。 我们想知道它的任何基类型是否都有。 因此我们应该使用Any
:
static bool AnyBaseType(this Type type, Func predicate) => type.BaseTypes().Any(predicate);
现在我们有另一个有用的工具。
我们想知道特定类型是否是特定的generics:
static bool IsParticularGeneric(this Type type, Type generic) => type.IsGenericType && type.GetGenericTypeDefinition() == generic;
我们想知道某个特定类型是否是一个监听器:
static bool IsListener(Type type) => type.IsParticularGeneric(typeof(Listener<>));
现在我们拥有了我们需要的工具。
var listeners = from assembly in AppDomain.CurrentDomain.GetAssemblies() from type in assembly.GetTypes() where type.AnyBaseType(IsListener) select type;
当您构建一次需要的工具时,查看查询的读取容易程度如何? 我们想知道什么? 如果任何基类型是监听器 。 那么代码是如何读取的? “任何基类型都是监听器的类型” – 代码读起来就像它的作用描述。
你可以找出任何基类型是一个Listener<>
,通过递归检查是目标类型IsInheritedFrom
它:
上述就是C#学习教程:如何使用C#中的reflection查找实现generics抽象类的所有类?分享的全部内容,如果对大家有所用处且需要了解更多关于C#学习教程,希望大家多多关注—计算机技术网(www.ctvol.com)!
public static class Extension { public static bool IsInheritedFrom(this Type type, Type Lookup) { var baseType = type.BaseType; if (baseType == null) return false; if (baseType.IsGenericType && baseType.GetGenericTypeDefinition() == Lookup) return true; return baseType.IsInheritedFrom(Lookup); } } var lookup = typeof(Listener<>); var listeners = AppDomain.CurrentDomain.GetAssemblies() .SelectMany(assembly => assembly.GetTypes()) .Where(x => x.IsClass && !x.IsAbstract && x.IsInheritedFrom(lookup)) .ToList();
本文来自网络收集,不代表计算机技术网立场,如涉及侵权请联系管理员删除。
ctvol管理联系方式QQ:251552304
本文章地址:https://www.ctvol.com/cdevelopment/961546.html