標籤:
Assembly和AppDomain的一些關於動態載入程式集的函數有些令人頭疼,但細細研究後還是可以將他們區分的。 這些函數大致可以分為四類:
第一類:載入到Load Context內
Load Context:
- Load Context是所有動態載入程式集首選應該被載入到的地方。
- 它只能載入在AppDomain資訊中的ApplicationBase目錄以及附帶的PrivateBinPath目錄內的程式集(關於這兩個目錄:可以參考另一篇文章:http://www.cnblogs.com/mgen/archive/2011/05/02/2034371.html)
執行這個操作的方法是:
Assembly.Load(AssemblyName)
Assembly.Load(string 程式集名稱)
注意上面的字串參數是程式集名稱,而不是路徑,程式集名稱可以直接是簡寫的程式集名稱,或是完整的名稱比如(SampleAssembly, Version=1.0.2004.0, Culture=neutral, PublicKeyToken=8744b20f8da049e3)(不帶括弧)
間接調用上面方法的其他方法有:
AppDomain類
Load(AssemblyName)
Load(string 程式集名稱)
ExecuteAssemblyByName(string 程式集名稱)
CreateInstance(...)
Activator類
CreateInstance(...)
進行一個小測試
string assName = "mbody";
//這是程式集名稱,不是路徑
string pLocal = Path.Combine(Environment.CurrentDirectory, "mbody.dll");
//這是路徑
var load = Assembly.Load(assName);
//用程式集名稱載入
var load2 = Assembly.Load(new AssemblyName() { CodeBase = pLocal });
//用路徑
Console.WriteLine(load == load2); //True
第二類:載入到LoadFrom Context內
LoadFrom Context
- 主要用來載入不在ApplicationBase目錄以及附帶的PrivateBinPath目錄內的程式集
- 不可以指定程式集版本或其他資訊
- 如果在LoadFrom Context中已經有一個具有相同程式集名稱的程式集(即使實際程式集路徑不一樣),LoadFrom仍然會返回已經載入的程式集
執行這個操作的方法是:
Assembly.LoadFrom(string 組件檔路徑, ...)
這裡的字串參數是檔案路徑。
間接調用上面方法的其他方法有:
AppDomain類
CreateInstanceFrom(string 組件檔路徑, ...)
Activator類
CreateInstanceFrom(string 組件檔路徑, ...)
小測試
//這幾個檔案都是同一個程式集
string pLocal = Path.Combine(Environment.CurrentDirectory, "mbody.dll");
var load = Assembly.Load("mbody");
var loadFromloc = Assembly.LoadFrom(pLocal);
var loadFrom = Assembly.LoadFrom("c:\\mbody.dll");
var loadFrom2 = Assembly.LoadFrom("C:\\mbody2.dll");
Console.WriteLine(load == loadFromloc);
Console.WriteLine(loadFrom == loadFrom2);
Console.WriteLine(load == loadFrom);
//(load == loadFromLoc) != (loadFrom == loadFrom2)
第三類:反射Context
反射Context
- 這裡載入的程式集不能執行,類的靜態建構函式也不執行,一般用來進行反射操作。
屬於這一類的方法有:
Assembly.ReflectionOnlyLoad(string 程式集名稱) (byte[])
Assembly.ReflectionOnlyLoadFrom(string 組件檔路徑)
第四類:不屬於任何Context
不屬於任何Context
- 用來載入LoadFrom無法載入的具有相同程式集名稱但是路徑不同的程式集
- 可以是通過位元組數組載入,也可能是Reflection.Emit產生的不在磁碟的程式集
- 具有很多的限制
屬於這一類的方法有:
Assembly.Load(byte[])
Assembly.LoadFile(string 組件檔路徑)
AppDomain.ExecuteAssembly(string 組件檔路徑, ...)
測試 :
//這幾個檔案都是同一個程式集
string pLocal = Path.Combine(Environment.CurrentDirectory, "mbody.dll");
var load = Assembly.Load("mbody");
var loadFileloc = Assembly.LoadFrom(pLocal);
var loadFile = Assembly.LoadFile("c:\\mbody.dll");
var loadFile2 = Assembly.LoadFile("C:\\mbody2.dll");
Console.WriteLine(load == loadFileloc);
Console.WriteLine(loadFile == loadFile2);
Console.WriteLine(load == loadFile);
//(load == loadFromLoc) != (loadFrom != loadFrom2)
更多可以參考MSDN(見備忘):http://msdn.microsoft.com/zh-cn/library/1009fa28.aspx
Assembly中Load, LoadFrom, LoadFile以及AppDomain, Activator類中相應函數的區別