C#反射:如何加载不同文件夹中的多个程序集
解决Assembly.LoadFrom加载程序集时依赖程序集找不到的问题
当你用Assembly.LoadFrom加载主程序集,反射时遇到依赖程序集找不到的FileNotFoundException,又不能用app.config配置,可以通过以下几种编程方式解决:
方法一:注册AppDomain的AssemblyResolve事件
CLR在找不到依赖程序集时会触发AssemblyResolve事件,你可以在事件回调中手动指定路径加载缺失的程序集。
// 在加载主程序集之前注册事件 AppDomain.CurrentDomain.AssemblyResolve += (sender, resolveArgs) => { var assemblyName = new AssemblyName(resolveArgs.Name); // 拼接依赖程序集的完整路径,替换为你的实际文件夹路径 var targetPath = Path.Combine(@"C:\YourReferencedAssembliesDir", $"{assemblyName.Name}.dll"); if (File.Exists(targetPath)) { return Assembly.LoadFrom(targetPath); } // 找不到则返回null,让CLR继续尝试默认查找逻辑 return null; }; // 加载主程序集 var mainAssembly = Assembly.LoadFrom(@"C:\MainAssemblyDir\Main.dll"); // 后续反射操作...
如果依赖分布在多个文件夹,可以在回调里遍历这些文件夹查找,或者根据程序集名称做路径映射,灵活调整查找逻辑。
方法二:预加载所有依赖程序集
加载主程序集后,主动获取其所有引用的程序集名称,然后从指定路径逐个加载:
var mainAssembly = Assembly.LoadFrom(@"C:\MainAssemblyDir\Main.dll"); // 遍历主程序集的所有直接引用 foreach (var refAssemblyName in mainAssembly.GetReferencedAssemblies()) { var refPath = Path.Combine(@"C:\YourReferencedAssembliesDir", $"{refAssemblyName.Name}.dll"); if (File.Exists(refPath)) { // 加载依赖程序集到当前AppDomain Assembly.LoadFrom(refPath); } } // 现在反射操作可以找到依赖中的类型了
这种方式适合依赖层级简单的场景,如果存在间接依赖(即依赖的依赖),可能需要递归遍历所有引用的程序集,或者结合AssemblyResolve事件兜底。
注意事项
- 确保程序对目标文件夹有读取权限,否则会加载失败。
- 如果依赖程序集包含版本号,注意
AssemblyName中的版本信息是否和文件匹配,必要时调整文件名拼接逻辑。 - 避免重复加载程序集,可以在
AssemblyResolve回调中先检查AppDomain.CurrentDomain.GetAssemblies(),确认是否已加载目标程序集。
内容的提问来源于stack exchange,提问作者user788454
相关产品推荐
相关产品推荐

