Подтвердить что ты не робот

Assembly.GetTypes() выбрасывает исключение

Что делает сборка GetTypes() за кулисами? Предполагая, что сборка загружена в AppDomain, все еще нужно читать из физической библиотеки DLL? И что делает манифест сборки?

Итерация через сборку:

AppDomain.CurrentDomain.GetAssemblies().SelectMany(a => a.GetTypes()) 

Я иногда получаю следующую ошибку:

 Could not load file or assembly 

Что говорит мне, что, поскольку сборка загружена в AppDomain, она не обязательно полностью загружается в память. Иногда ему все равно нужно вернуться к файлу.

Мои вопросы:

  • Почему он это делает?
  • Что я могу сделать, чтобы обнаружить эти полузагруженные сборки?
4b9b3361

Ответ 1

Получение типа из сборки может потребовать загрузки дополнительных сборок, что, вероятно, является причиной ошибки; неспособность загрузить зависимую сборку. Однако сборка .NET может быть построена из нескольких модулей в разных файлах, поэтому я считаю, что вы также можете столкнуться с этой проблемой, если у вас есть сборка multifile assembly и одна или больше файлов отсутствуют или повреждены.

Связанный с ошибкой вы должны получить больше информации о конкретной сборке, которая не может быть загружена.

Если вы просто хотите загрузить список загружаемых типов в сборке, вы можете использовать метод расширения следующим образом:

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);
    }
}

(Источник: Получить все типы в сборке)

Ответ 2

За кулисами метод GetType возвращает адрес, хранящийся в указанном объекте указателя объекта объекта (когда объект хранится в куче, эта информация сохраняется вместе с несколькими другими, такими как Sync Block Index). Так метод GetType возвращает истинный тип любого объекта. Сборка может зависеть от какой-либо другой сборки, которая должна быть загружена. И если это не требуется приложением, оно не будет загружено JIT. Итак, да, это требует, чтобы сборки были физически доступны в любое время.