c#-在所有程序集中查找类型

我需要在网站或Windows应用程序的所有程序集中查找特定类型,有没有简便的方法? 就像ASP.NET MVC的控制器工厂在控制器的所有程序集中的外观一样。

谢谢。

Brian Mains asked 2019-11-06T17:38:37Z
4个解决方案
97 votes

有两个步骤可以实现此目的:

  • 26025526293225809809为您提供了当前应用程序域中加载的所有程序集。
  • Assembly类提供了GetTypes()方法来检索该特定程序集中的所有类型。

因此,您的代码可能如下所示:

foreach (Assembly a in AppDomain.CurrentDomain.GetAssemblies())
{
    foreach (Type t in a.GetTypes())
    {
        // ... do something with 't' ...
    }
}

要查找特定类型(例如,实现给定的接口,从共同祖先继承的东西或其他东西),您必须过滤掉结果。 如果您需要在应用程序中的多个位置上执行此操作,则最好构建一个提供不同选项的帮助程序类。 例如,我通常应用名称空间前缀过滤器,接口实现过滤器和继承过滤器。

有关详细文档,请在此处和此处查看MSDN。

Ondrej Tucny answered 2019-11-06T17:39:26Z
29 votes

易于使用Linq:

IEnumerable<Type> types =
            from a in AppDomain.CurrentDomain.GetAssemblies()
            from t in a.GetTypes()
            select t;

foreach(Type t in types)
{
    ...
}
Thomas Levesque answered 2019-11-06T17:39:50Z
28 votes

LINQ解决方案,其中检查程序集是否动态:

/// <summary>
/// Looks in all loaded assemblies for the given type.
/// </summary>
/// <param name="fullName">
/// The full name of the type.
/// </param>
/// <returns>
/// The <see cref="Type"/> found; null if not found.
/// </returns>
private static Type FindType(string fullName)
{
    return
        AppDomain.CurrentDomain.GetAssemblies()
            .Where(a => !a.IsDynamic)
            .SelectMany(a => a.GetTypes())
            .FirstOrDefault(t => t.FullName.Equals(fullName));
}
mheyman answered 2019-11-06T17:40:14Z
7 votes

最常见的是,您只对从外部可见的装配感兴趣。 因此,您需要调用GetExportedTypes(),但除此之外,还可以引发ReflectionTypeLoadException。 以下代码可解决这些情况。

public static IEnumerable<Type> FindTypes(Func<Type, bool> predicate)
{
    if (predicate == null)
        throw new ArgumentNullException(nameof(predicate));

    foreach (var assembly in AppDomain.CurrentDomain.GetAssemblies())
    {
        if (!assembly.IsDynamic)
        {
            Type[] exportedTypes = null;
            try
            {
                exportedTypes = assembly.GetExportedTypes();
            }
            catch (ReflectionTypeLoadException e)
            {
                exportedTypes = e.Types;
            }

            if (exportedTypes != null)
            {
                foreach (var type in exportedTypes)
                {
                    if (predicate(type))
                        yield return type;
                }
            }
        }
    }
}
alex.pino answered 2019-11-06T17:40:38Z
translate from https://stackoverflow.com:/questions/4692340/find-types-in-all-assemblies