Answers:
是。您需要用于Assembly.LoadFrom
将程序集加载到内存中,然后可以用于Activator.CreateInstance
创建首选类型的实例。您需要首先使用反射查找类型。这是一个简单的示例:
Assembly assembly = Assembly.LoadFrom("MyNice.dll");
Type type = assembly.GetType("MyType");
object instanceOfMyType = Activator.CreateInstance(type);
当您具有程序集文件名和类型名称时,可以Activator.CreateInstance(assemblyName, typeName)
用来要求.NET类型解析将其解析为类型。您可以使用try / catch将其包装起来,以便在失败时可以对目录进行搜索,在其中可以专门存储其他程序集,否则可能无法搜索到其他程序集。此时将使用前面的方法。
Type type = assembly.GetType("MyNamespace"+"."+"MyType");
Activator.CreateInstance应该可以工作。
IFace object = (IFace)Activator.CreateInstance( "AssemblyName",
"TypeName" )
.Unwrap();
注意:类型名称必须是标准类型。
例:
var aray = (IList)Activator.CreateInstance("mscorlib","System.Collections.ArrayList").Unwrap();
aray.Add(10);
foreach (object obj in aray)
{
Console.WriteLine(obj);
}
TypeName
必须完全合格。我必须这样称呼:Activator.CreateInstance("MyAssembly","MyAssembly.TypeName")
并且返回一个ObjectHandle
。要进入您的界面,您需要做ObjectHandle.UnWrap()
我发现此问题和一些答案非常有用,但是我确实遇到了路径问题,因此此答案将通过查找bin目录路径来涵盖加载库。
第一个解决方案:
string assemblyName = "library.dll";
string assemblyPath = HttpContext.Current.Server.MapPath("~/bin/" + assemblyName);
Assembly assembly = Assembly.LoadFrom(assemblyPath);
Type T = assembly.GetType("Company.Project.Classname");
Company.Project.Classname instance = (Company.Project.Classname) Activator.CreateInstance(T);
第二解决方案
string assemblyName = "library.dll";
string assemblyPath = HttpContext.Current.Server.MapPath("~/bin/" + assemblyName);
Assembly assembly = Assembly.LoadFile(assemblyPath);
(Company.Project.Classname) instance = (Company.Project.Classname) assembly.CreateInstance("Company.Project.Classname");
您可以对接口使用相同的原理(您将创建一个类,但强制转换为接口),例如:
(Company.Project.Interfacename) instance = (Company.Project.Interfacename) assembly.CreateInstance("Company.Project.Classname");
此示例适用于Web应用程序,但类似示例可用于桌面应用程序,仅以不同的方式解析路径,例如
Path.GetDirectoryName(Application.ExecutablePath)
这很容易。
来自MSDN的示例:
public static void Main()
{
// Use the file name to load the assembly into the current
// application domain.
Assembly a = Assembly.Load("example");
// Get the type to use.
Type myType = a.GetType("Example");
// Get the method to call.
MethodInfo myMethod = myType.GetMethod("MethodA");
// Create an instance.
object obj = Activator.CreateInstance(myType);
// Execute the method.
myMethod.Invoke(obj, null);
}
这是参考链接
从Framework v4.5开始,您可以使用Activator.CreateInstanceFrom()轻松实例化程序集中的类。下面的示例演示如何使用它以及如何调用传递参数并获取返回值的方法。
// Assuming moduleFileName contains full or valid relative path to assembly
var moduleInstance = Activator.CreateInstanceFrom(moduleFileName, "MyNamespace.MyClass");
MethodInfo mi = moduleInstance.Unwrap().GetType().GetMethod("MyMethod");
// Assuming the method returns a boolean and accepts a single string parameter
bool rc = Convert.ToBoolean(mi.Invoke(moduleInstance.Unwrap(), new object[] { "MyParamValue" } ));
您可以使用* Assembly.Load **方法加载程序集。使用Activator.CreateInstance可以创建所需类型的新实例。请记住,您必须使用要加载的类的全类型名称(例如Namespace.SubNamespace.ClassName)。使用方法InvokeMember中的类型类,你可以调用该类型的方法。
另外,考虑到一旦加载,就不能卸载程序集,直到整个AppDomain也都卸载为止(这基本上是内存泄漏)。
根据此类功能对您的项目的内在程度,您可能需要考虑使用诸如MEF之类的东西,它将为您处理组件的加载和绑定。
Assembly assembly = Assembly.LoadFrom("MyAssembly.dll");
Type type = assembly.GetType("MyType");
dynamic instanceOfMyType = Activator.CreateInstance(type);
因此,通过这种方式,您可以将函数与获取methodinfo一起使用,然后对其进行调用。但是您不能使用Intellisense,因为动态类型是在运行时而不是在编译时键入的。