C# 反射
发布时间:2020-12-15 22:40:45 所属栏目:百科 来源:网络整理
导读:反射: 反射指程序可以访问、检测和修改它本身状态或行为的一种能力。 程序集包含模块,而模块包含类型,类型又包含成员。反射则提供了封装程序集、模块和类型的对象。 您可以使用反射动态地创建类型的实例,将类型绑定到现有对象,或从现有对象中获取类型。
反射: 反射指程序可以访问、检测和修改它本身状态或行为的一种能力。 程序集包含模块,而模块包含类型,类型又包含成员。反射则提供了封装程序集、模块和类型的对象。 您可以使用反射动态地创建类型的实例,将类型绑定到现有对象,或从现有对象中获取类型。然后,可以调用类型的方法或访问其字段和属性。 优缺点优点:
缺点:
可通过类名、成员的名字类进行对象的实例化、操作类成员
取得Assembly的方法:
Assembly.Load
Assembly.LoadFile
Assembly.LoadFrom
Type对象的Assembly方法
反射的成员:
(1)使用Assembly定义和加载程序集,加载在程序集清单中列出模块,以及从此程序集中查找类型并创建该类型的实例。
(2)使用Module了解包含模块的程序集以及模块中的类等,还可以获取在模块上定义的所有全局方法或其他特定的非全局方法。
(3)使用ConstructorInfo了解构造函数的名称、参数、访问修饰符(如pulic 或private)和实现详细信息(如abstract或virtual)等。
(4)使用MethodInfo了解方法的名称、返回类型、参数、访问修饰符(如pulic 或private)和实现详细信息(如abstract或virtual)等。
(5)使用FiedInfo了解字段的名称、访问修饰符(如public或private)和实现详细信息(如static)等,并获取或设置字段值。
(6)使用EventInfo了解事件的名称、事件处理程序数据类型、自定义属性、声明类型和反射类型等,添加或移除事件处理程序。
(7)使用PropertyInfo了解属性的名称、数据类型、声明类型、反射类型和只读或可写状态等,获取或设置属性值。
(8)使用ParameterInfo了解参数的名称、数据类型、是输入参数还是输出参数,以及参数在方法签名中的位置等。
?
常用类:
System.Type 类//通过这个类可以访问任何给定数据类型的信息。
Type类的属性:
Name 数据类型名
FullName 数据类型的完全限定名(包括命名空间名)
Namespace 定义数据类型的命名空间名
IsAbstract 指示该类型是否是抽象类型
IsArray 指示该类型是否是数组
IsClass 指示该类型是否是类
IsEnum 指示该类型是否是枚举
IsInterface 指示该类型是否是接口
IsPublic 指示该类型是否是公有的
IsSealed 指示该类型是否是密封类
IsValueType 指示该类型是否是值类型
Type类的方法:
GetConstructor(),GetConstructors():返回ConstructorInfo类型,用于取得该类的构造函数的信息
GetEvent(),GetEvents():返回EventInfo类型,用于取得该类的事件的信息
GetField(),GetFields():返回FieldInfo类型,用于取得该类的字段(成员变量)的信息
GetInterface(),GetInterfaces():返回InterfaceInfo类型,用于取得该类实现的接口的信息
GetMember(),GetMembers():返回MemberInfo类型,用于取得该类的所有成员的信息
GetMethod(),GetMethods():返回MethodInfo类型,用于取得该类的方法的信息
GetProperty(),GetProperties():返回PropertyInfo类型,用于取得该类的属性的信息
可以调用这些成员,其方式是调用Type的InvokeMember()方法,或者调用MethodInfo,PropertyInfo和其他类的Invoke()方法。
System.Reflection.Assembly类//它可以用于访问给定程序集的信息,或者把这个程序集加载到程序中。
先创建一个类
class person//默认partial { public int show(int a) { return a; } public string show(int a,double c) { return a+""+c; } public void showA() { } public static void ShowB() { } private void ShowC() { } private static void ShowD() { } public int a; public static int b; private int c; private static int d; private person(int a,string B) { Console.WriteLine(a + "person类有参函数被调用" + B); } public person() { Console.WriteLine("person类无参函数被调用"); } }
现在开始调用
//通常person p=new person(); //反射: /*BindingFlags: 要访问的方法或字段的权限描述 ,必须要同时具备两个描述 1.要有要访问的成员的访问权限描述 2.要有访问的成员的归属 (静态的是Static 非静态是Instance) */ //通过类名获取一个类型 注意:命名空间 Type T = Type.GetType("ConsoleApp1.person"); //默认会使用public 权限的无参构造方法来实例化 object obj = Activator.CreateInstance(T); //若为true 表示可以匹配任何权限的无参构造函数 object obj1 = Activator.CreateInstance(T,true); //public 权限的 有参构造方法 //object obj2 = Activator.CreateInstance(T,2,"aaa"); //非public 权限的 有参构造方法 object obj3 = Activator.CreateInstance(T,System.Reflection.BindingFlags.NonPublic | BindingFlags.Instance,null,new Object[] { 1,"BBB" },null); //通过反射访问类中的字段 //1 public 非静态 a FieldInfo a = T.GetField("a"); a.SetValue(obj,2); Object aa = a.GetValue(obj); //2访问public 静态 b FieldInfo b = T.GetField("b",BindingFlags.Public | BindingFlags.Static); b.SetValue(null,3);//要访问的是一个静态成员 访问主体是null object bb = b.GetValue(obj); //3访问public 非静态 c FieldInfo c = T.GetField("c",BindingFlags.NonPublic | BindingFlags.Instance); c.SetValue(obj,5); object cc = c.GetValue(obj); //4访问private 静态 d FieldInfo d = T.GetField("d",BindingFlags.NonPublic | BindingFlags.Static); d.SetValue(null,6);//要访问的是一个静态成员 访问主体是null object dd = d.GetValue(obj); //通过反射访问方法 //public 方法A MethodInfo method = T.GetMethod("ShowD",BindingFlags.NonPublic | BindingFlags.Static); method.Invoke(null,null); //public 静态方法 //private 方法C //private 静态方法 //获取有参函数 注意:字符串的大小写 MethodInfo info = T.GetMethod("show",BindingFlags.Public | BindingFlags.Instance,new Type[] { typeof(int) },null); //type 数组传 方法的参数列表 object x = info.Invoke(obj,new object[] { 1 }); Console.WriteLine(x); 当然了还有很多时候是要通过exe? 或者dll? 来操作的 这里新建了一个控制台应用程序 在main 方法中?Console.WriteLine("要输出的内容"); 并且将main 函数中的参数改为无参的 string dllName = "ConsoleApp2";//指定dll文件的名字 程序集的名字 string FullName = "ConsoleApp2.Program";//指定程序及的名字+类的名字 Assembly assembly = Assembly.Load(dllName);//加载程序集 Type type = assembly.GetType(FullName);//从程序集中获取指定对象的类型 object xa = Activator.CreateInstance(type);//创建实例 MethodInfo methodx = type.GetMethod("Main",BindingFlags.NonPublic | BindingFlags.Static); methodx.Invoke(null,null);//这里如果说在ConsoleApp2 中main函数是传入参数要对应 /*static void Main(string[] args) { } */ ?参考:https://www.bilibili.com/video/av29432157?t=1973? 、https://www.runoob.com/csharp/csharp-reflection.html (编辑:李大同) 【声明】本站内容均来自网络,其相关言论仅代表作者个人观点,不代表本站立场。若无意侵犯到您的权利,请及时与联系站长删除相关内容! |