如何使用反射呢?
我们先来定义一个类,然后编译得到一个dll文件,实例代码如下所示
using System; using System.Collections.Generic; using System.Text; namespace ClassLibrary1 { public class DataAccess { //文件需要编译为dll文件,可以使用VS环境 //控制台的编译命令csc /target:library ClassLibrary1.cs{源文件的名称} string name; int age; public DataAccess() { Console.WriteLine("无参数构造函数被调用,实例已经创建"); } public DataAccess(string strName) { this.name = strName; Console.WriteLine("有一个参数构造函数被调用,name={0}", name); } public DataAccess(string strName, int intAge) { this.name = strName; this.age = intAge; Console.WriteLine("有两个参数构造函数被调用,name={0},age={1}", strName, intAge); } //普通方法 public void Fun1() { Console.WriteLine("No ReturnVale"); } //带返回值的 public string Fun2() { return "Hello World!"; } //一个参数 public void Fun3(string name) { Console.WriteLine(name); } //同类型的参数 public void Fun4(int x, int y) { Console.WriteLine("x={0},y={1}", x, y); } //不同类型的参数 public void Fun5(string my_name, int my_Age) { Console.WriteLine("strName={0},Age={1}", my_name, my_Age); } //静态方法的调用 public static void Fun6() { Console.WriteLine("Static Method"); } } }
注意:可以使用控制台的编译命令csc /target:library ClassLibrary1.cs{源文件的名称}
编译完成之后将dll文件copy到你项目的根目录bin下面【我们在这里不添加引用的】
ok!准备使用
步骤如下
第一步:将你要反射的dll文件,拷贝到当前程序的bin目录下
string strDllPath = AppDomain.CurrentDomain.BaseDirectory + "ClassLibrary1.dll";
第二步:加载当前应用程序集
//获取程序集对象
Assembly assembly = Assembly.LoadFrom(strDllPath);
// 我们可以显示程序集的属性信息
// 获取程序集的显示名称。
string name = assembly.FullName;
// 获取最初指定的程序集的位置
string CodeBase = assembly.CodeBase;
Console.WriteLine(string.Format("程序集的显示名称:{0};\n程序集的位置:{1}", name, CodeBase));
//第三步:获取一个类的类型
Type t = assembly.GetType("ClassLibrary1.DataAccess");
//第四步:通过创建器创建类型的实例对象
使用无参数的构造函数构造实例
object obj = Activator.CreateInstance(t); //DataAccess的构造函数已经执行
使用一个参数的构造函数构造实例
object obj2 = Activator.CreateInstance(t, "Data");
//多个参数的构造,直接在后面添加即可(方法中有参数数组,直接写入类型匹配的参数即可)
object obj3 = Activator.CreateInstance(t, "Tom", 12);
现在内类的实例已经准备ok了?如果你运行项目的话,会看到相关函数的执行的
如何去调用方法?通过Invoke方法调用(获取方法返回值)
通过类型去查找指定的方法(传入方法的名称不要加括号)。方法的类型:有返回值的方法;无返回值类型的方法
1.普通无参数无返回值调用
MethodInfo mi = t.GetMethod("Fun1");
mi.Invoke(obj, null);//参数说明:该类的实例对象,方法参数,没有参数为空
2.普通无参数带返回值调用
MethodInfo mi2 = t.GetMethod("Fun2");
object return1 = mi2.Invoke(obj, null);//得到你的返回值
Console.WriteLine(return1.ToString());
3.有参数无返回值的的调用
我们需要一个参数,向方法传参数需要构造参数数组
object[] arrObj1 = new object[] { "This is a params" };
MethodInfo mi3 = t.GetMethod("Fun3");
mi3.Invoke(obj, arrObj1);
4.多个同类型的参数
object[] intobj = new object[2] { 12, 67 };
MethodInfo mi4 = t.GetMethod("Fun4");
mi4.Invoke(obj, intobj);
5.多个不同类型的参数
object[] difobj = new object[2] { "Liming", 12 };
MethodInfo mi5 = t.GetMethod("Fun5");
object reVal = mi5.Invoke(obj, difobj);
简单来说就是如果你要想调用有参数的方法那么就需要构造一个参数数组,想方法中传递参数,通过 mi5.Invoke(obj, difobj);获得返回值
静态方法如何调用呢?
静态方法的调用 通过类名去调用
MethodInfo mi6 = t.GetMethod("Fun6");
mi6.Invoke(t, null); //这里就不是obj了注意
//包含的层次关系:程序集---类(类的实例对象)----方法
完成的方法如下:可以拷贝直接使用
public static void MyFun() { //第一步:将你要反射的dll文件,拷贝到当前程序的bin目录下 string strDllPath = AppDomain.CurrentDomain.BaseDirectory + "ClassLibrary1.dll"; //第二步:加载当前应用程序集 //获取程序集对象 Assembly assembly = Assembly.LoadFrom(strDllPath); // 显示程序集的属性信息 // 获取程序集的显示名称。 string name = assembly.FullName; // 获取最初指定的程序集的位置 string CodeBase = assembly.CodeBase; Console.WriteLine(string.Format("程序集的显示名称:{0};\n程序集的位置:{1}", name, CodeBase)); //第三步:获取一个类的类型 Type t = assembly.GetType("ClassLibrary1.DataAccess"); //第四步:通过创建器创建类型的实例对象 //使用无参数的构造函数构造实例 object obj = Activator.CreateInstance(t); //DataAccess的构造函数已经执行 //使用一个参数的构造函数构造实例 object obj2 = Activator.CreateInstance(t, "Data"); //多个参数的构造,直接在后面添加即可(方法中有参数数组,直接写入类型匹配的参数即可) object obj3 = Activator.CreateInstance(t, "Tom", 12); //如何去调用方法?通过Invoke方法调用(获取方法返回值) //通过类型去查找指定的方法(传入方法的名称不要加括号)。方法的类型:有返回值的方法;无返回值类型的方法 //1.普通无参数无返回值调用 MethodInfo mi = t.GetMethod("Fun1"); mi.Invoke(obj, null);//参数说明:该类的实例对象,方法参数,没有参数为空 //2.普通无参数带返回值调用 MethodInfo mi2 = t.GetMethod("Fun2"); object return1 = mi2.Invoke(obj, null);//得到你的返回值 Console.WriteLine(return1.ToString()); //3.有参数无返回值的的调用 //需要一个参数,向方法传参数需要构造参数数组 object[] arrObj1 = new object[] { "This is a params" }; MethodInfo mi3 = t.GetMethod("Fun3"); mi3.Invoke(obj, arrObj1); //4.多个同类型的参数 object[] intobj = new object[2] { 12, 67 }; MethodInfo mi4 = t.GetMethod("Fun4"); mi4.Invoke(obj, intobj); //5.多个不同类型的参数 object[] difobj = new object[2] { "Liming", 12 }; MethodInfo mi5 = t.GetMethod("Fun5"); object reVal = mi5.Invoke(obj, difobj); //静态方法的调用 通过类名去调用 MethodInfo mi6 = t.GetMethod("Fun6"); mi6.Invoke(t, null); //这里就不是obj了注意 //包含的层次关系:程序集---类(类的实例对象)----方法 }