C# Assembly.GetTypes()引发异常

C# Assembly.GetTypes()引发异常,c#,.net,reflection,C#,.net,Reflection,assemblyGetTypes()在幕后做什么?假设程序集已加载到AppDomain中,它是否仍需要从物理DLL中读取?程序集清单是做什么的 像这样迭代程序集: AppDomain.CurrentDomain.GetAssemblies().SelectMany(a => a.GetTypes()) public static IEnumerable<Type> GetLoadableTypes(this Assembly assembly) { if (asse

assembly
GetTypes()
在幕后做什么?假设程序集已加载到
AppDomain
中,它是否仍需要从物理DLL中读取?程序集清单是做什么的

像这样迭代程序集:

AppDomain.CurrentDomain.GetAssemblies().SelectMany(a => a.GetTypes()) 
public static IEnumerable<Type> GetLoadableTypes(this Assembly assembly)
{
    if (assembly == null) throw new ArgumentNullException(nameof(assembly));
    try
    {
        return assembly.GetTypes();
    }
    catch (ReflectionTypeLoadException e)
    {
        return e.Types.Where(t => t != null);
    }
}
我偶尔会遇到以下错误:

 Could not load file or assembly 
这告诉我,由于程序集加载到
AppDomain
中,因此它不一定完全加载到内存中。有时它仍然需要返回到文件

我的问题是:

  • 它为什么这样做
  • 如何检测这些半加载的部件

  • 从程序集获取类型可能需要加载其他程序集,因此这很可能是错误的原因;未能加载从属程序集。但是,一个.NET程序集可能是由不同文件中的多个模块构成的,因此我相信,如果您有一个或多个文件丢失或损坏,您也可能会面临此问题

    与此错误关联,您应该获得有关无法加载的特定程序集的更多信息

    如果只想在程序集中加载可加载类型的列表,可以使用如下扩展方法:

    AppDomain.CurrentDomain.GetAssemblies().SelectMany(a => a.GetTypes()) 
    
    public static IEnumerable<Type> GetLoadableTypes(this Assembly assembly)
    {
        if (assembly == null) throw new ArgumentNullException(nameof(assembly));
        try
        {
            return assembly.GetTypes();
        }
        catch (ReflectionTypeLoadException e)
        {
            return e.Types.Where(t => t != null);
        }
    }
    
    公共静态IEnumerable GetLoadableTypes(此程序集)
    {
    如果(assembly==null)抛出新的ArgumentNullException(nameof(assembly));
    尝试
    {
    返回assembly.GetTypes();
    }
    捕获(ReflectionTypeLoadException e)
    {
    返回e.Types.Where(t=>t!=null);
    }
    }
    

    (来源:)

    在后台,GetType方法返回存储在指定对象的type对象指针成员中的地址(当对象存储在堆中时,此信息与其他两个信息(如同步块索引)一起存储)。这就是GetType方法返回任何对象的真实类型的方式。程序集可能依赖于必须加载的其他程序集。除非应用程序需要,否则JIT不会加载它。因此,是的,它要求程序集始终在物理上可用。

    这不适用于加载到经典.net运行时的核心DLL。您可以加载,但不能浏览类型。