LoadFrom是将DLL加载到当前上下文环境中,如果当前上下文环境中已有该DLL,则返回先前的DLL.也就是说对于同一版本的DLL,上下文只加载一次.
LoadFile则是可以加载多次.

假设:

a.dll 中有一个接口 interface a
b.dll 中有一个类实现了该接口 class b : a
c.exe 在程序内引用了a.dll

1、Assembly.LoadFile只载入相应的dll文件,比如Assembly.LoadFile("b.dll"),则载入b.dll,假如b.dll中引用了a.dll的话,a.dll并不会被载入。
Assembly.LoadFrom则不一样,它会载入dll文件及其引用的其他dll,比如上面的例子,a.dll也会被载入。
2、用Assembly.LoadFrom载入一个Assembly时,会先检查前面是否已经载入过相同名字的Assembly,比如a.dll有两个版本(版本1在目录1下,版本2放在目录2下),程序一开始时载入了版本1,当使用Assembly.LoadFrom("2\\a.dll")载入版本2时,不能载入,而是返回版本1。
Assembly.LoadFile的话则不会做这样的检查,比如上面的例子换成Assembly.LoadFile的话,则能正确载入版本2

然后在启动后运行时LoadFrom a.dll和b.dll后,实例化b对象时无法转化为a接口,如果不在运行时LoadFrom a.dll就不会有这个问题.
我使用AppDomain.CurrentDomain.GetAssemblies();在每次加载后都检测上下文中的Assembly数量,发现a.dll的确被加载了2次.

刚才LoadFrom不是说当当前上下文已有该DLL时就不加载吗?这是因为程序集启动时加载的dll和用loadfrom加载的dll。程序认为是两个dll。即b.dll 在程序内引用了a.dll,启动时就加载了a.dll,再LoadFrom a.dll,这里就是两个了;由于不知道应该转换为哪个a.dll的接口a,因此在转换时报错!

AppDomain.CurrentDomain.GetAssemblies 说明:获取已加载到此应用程序域的执行上下文中的程序集。
Assembly.LoadFile 说明:使用 LoadFile 方法来加载和检查具有相同标识但位于不同路径中的程序集。与 LoadFrom 不同,LoadFile 不会将文件加载到 LoadFrom 上下文中,也不会使用加载路径解析依赖项
当用LoadFile这个方法加载不同位置的a.dll后,在AppDomain.CurrentDomain.GetAssemblies()中都能看到每一个加载后的a.dll,但是执行转换时并不会出错.
怎样才能看到真正的"当前程序域的上下文中的程序集"呢,如何确定用的是哪个a.dll;应该是最后引用的那个,留待以后确认。

 


posted on 2010-12-17 16:23  飞翔-方向 积累 沉淀  阅读(1349)  评论(2)    收藏  举报