1、通过反射可以在运行时获得程序或程序集中每一个类型(包括类、结构、委托、接口和枚举)的成员和成员的信息。通过反射可以直接创建对象,即使这个对象的类型在编译时还不知道。
反射主要作用:
(1)、获取类型的相关信息
(2)、动态调用方法
(3)、动态构造对象
(4)、从程序集中获得类型
2、反射用到的命名空间:
using System.Reflection;
using System.Type;
using System.Reflection.Assembly;
3、System.Type类:通过这个类可以访问任何给定数据类型的信息。
1)、三种常用方式:
(1)、使用C# typeof运算符
格式:Type t = typeof(string);
eg、
Type t = typeof(string);
Console.WriteLine (t.Name);
Console.WriteLine (t.Namespace);
运算结果:String
System
(2)、使用对象GetType()方法
格式:string s = "gra";
Type t = s.GetType();
eg、
int i = 9;
t = i.GetType ();
Console.WriteLine (t.Name);
Console.WriteLine (t.Namespace);
运算结果:Int32
System
(3)、还可以调用Type类的静态方法GetType()
格式:Type t = Type.GetType("System.String");
eg、
t = Type.GetType ("System.String");
Console.WriteLine (t.Name);
Console.WriteLine (t.Namespace);
运算结果:String
System
2)、Type类的属性
(1)、Name --> 数据类型名
(2)、FullName --> 数据类型的完全限定名(包括命名空间名)
(3)、Namespace --> 定义数据类型的命名空间名
(4)、IsAbstract --> 指示该类型是否是抽象类型
(5)、IsArray --> 指示该类型是否是数组
(6)、IsClass --> 指示该类型是否是类
(7)、IsEnum --> 指示该类型是否是枚举
(8)、IsInterface --> 指示该类型是否是接口
(9)、IsPublic --> 指示该类型是否是公有的
(10)、IsSealed --> 指示该类型是否是密封类
(11)、IsValueType --> 指示该类型是否是值类型
3)、Type类的方法
(1)、GetConstructor()、GetConstructors() --> 返回ConstructorInfo类型,用于取得该类的构造函数的信息
eg、
public static void testConstructors()
{
Type t = typeof(Student);
var v = t.GetConstructors ();
foreach (var item in v)
{
//Console.WriteLine (item);
var paras = item.GetParameters ();
foreach (var i in paras)
Console.WriteLine (i.Name+"-"+i.ParameterType);
//i.Name,i的名字
//i.ParameterType,i的参数类型
}
}
(2)、GetEvent()、GetEvents() --> 返回EventInfo类型,用于取得该类的事件的信息
(3)、GetField()、GetFields() --> 返回FieldInfo类型,用于取得该类的字段(成员变量)的信息
eg、
public static void testField()
{
Type t = typeof(Student);
//GetFields 获取字段,返回为FieldInfo类型的数组
//只能获取到公有字段
FieldInfo[] f = t.GetFields ();
foreach (var item in f)
Console.WriteLine (item);
}
(4)、GetInterface()、GetInterfaces() --> 返回InterfaceInfo类型,用于取得该类实现的接口的信息
(5)、GetMember()、GetMembers() --> 返回MemberInfo类型,用于取得该类的所有成员的信息
eg、
public static void testMember()
{
Type t = typeof(Student);
var members = t.GetMembers ();
foreach (var item in members)
Console.WriteLine (item.MemberType+":"+item);//item.MemberType,显示成员的类型
}
(6)、GetMethod()、GetMethods() --> 返回MethodInfo类型,用于 取得该类的方法的信息
eg、
public static void testMethod()
{
Type t = typeof(Student);
var array= t.GetMethods ();
foreach (var item in array)
Console.WriteLine (item);
}
(7)、GetProperty()、GetProperties() --> 返回PropertyInfo类 型,用于取得该类的属性的信息
eg、
public static void testProperty()
{
Type t = typeof(Student);
PropertyInfo[] array= t.GetProperties ();
foreach (var v in array)
Console.WriteLine (v);
}
4)、用构造方法动态生成对象
eg、
public static void CreateObject()
{
Type t = typeof(Student);
Type[] types = new Type[]{ typeof(string), typeof(int), typeof(int) };
ConstructorInfo info = t.GetConstructor (types);
object[] objects = new object[]{ "Tom", 19, 1 };
Student s = (Student)info.Invoke (objects);
s.Show ();
}
5)、用Activator生成对象
eg、
public static void testActivator()
{
//生成对象必然会调用构造函数
//没有参数调用的无参的构造
Type t = typeof(Student);
Student s1 = (Student)Activator.CreateInstance (t);
s1.Show ();
//给构造函数传参
Type t1 = typeof(Student);
Student s2 = (Student)Activator.CreateInstance (t1,"Tom",15,2);
s2.Show ();
//用object数组来给构造函数的参数传值
Type t2 = typeof(Student);
object[] objects = new object[]{ "Jack", 19, 3 };
Student s3 = (Student)Activator.CreateInstance (t2, objects);
s3.Show ();
}
4、System.Reflection.Assembly类:它可以用于访问给定程序集的信息,或者把这个程序集加载到程序中。
通过Assembly获取程序集中所有的类:
Type[] t = ass.GetTypes();
eg、通过一个exe文件,获取其源码中的内容,并调用其函数
public static void testAssembly()
{
Assembly ay = Assembly.LoadFile ("/Users/neworigin/Desktop/Day20-2测试反射.exe");//引号内为exe文件的路径
//Console.WriteLine (ay.CodeBase);//打印路径
//获取类
// Type[] types = ay.GetTypes ();
// foreach (var t1 in types)
// Console.WriteLine (t1);
object o=ay.CreateInstance("Day202测试反射.Test");//引号内为(命名空间.类名)。
Type t = o.GetType ();
MethodInfo info = t.GetMethod ("print");//引号内为调用的函数名
info.Invoke (o, null);
}
反射主要作用:
(1)、获取类型的相关信息
(2)、动态调用方法
(3)、动态构造对象
(4)、从程序集中获得类型
2、反射用到的命名空间:
using System.Reflection;
using System.Type;
using System.Reflection.Assembly;
3、System.Type类:通过这个类可以访问任何给定数据类型的信息。
1)、三种常用方式:
(1)、使用C# typeof运算符
格式:Type t = typeof(string);
eg、
Type t = typeof(string);
Console.WriteLine (t.Name);
Console.WriteLine (t.Namespace);
运算结果:String
System
(2)、使用对象GetType()方法
格式:string s = "gra";
Type t = s.GetType();
eg、
int i = 9;
t = i.GetType ();
Console.WriteLine (t.Name);
Console.WriteLine (t.Namespace);
运算结果:Int32
System
(3)、还可以调用Type类的静态方法GetType()
格式:Type t = Type.GetType("System.String");
eg、
t = Type.GetType ("System.String");
Console.WriteLine (t.Name);
Console.WriteLine (t.Namespace);
运算结果:String
System
2)、Type类的属性
(1)、Name --> 数据类型名
(2)、FullName --> 数据类型的完全限定名(包括命名空间名)
(3)、Namespace --> 定义数据类型的命名空间名
(4)、IsAbstract --> 指示该类型是否是抽象类型
(5)、IsArray --> 指示该类型是否是数组
(6)、IsClass --> 指示该类型是否是类
(7)、IsEnum --> 指示该类型是否是枚举
(8)、IsInterface --> 指示该类型是否是接口
(9)、IsPublic --> 指示该类型是否是公有的
(10)、IsSealed --> 指示该类型是否是密封类
(11)、IsValueType --> 指示该类型是否是值类型
3)、Type类的方法
(1)、GetConstructor()、GetConstructors() --> 返回ConstructorInfo类型,用于取得该类的构造函数的信息
eg、
public static void testConstructors()
{
Type t = typeof(Student);
var v = t.GetConstructors ();
foreach (var item in v)
{
//Console.WriteLine (item);
var paras = item.GetParameters ();
foreach (var i in paras)
Console.WriteLine (i.Name+"-"+i.ParameterType);
//i.Name,i的名字
//i.ParameterType,i的参数类型
}
}
(2)、GetEvent()、GetEvents() --> 返回EventInfo类型,用于取得该类的事件的信息
(3)、GetField()、GetFields() --> 返回FieldInfo类型,用于取得该类的字段(成员变量)的信息
eg、
public static void testField()
{
Type t = typeof(Student);
//GetFields 获取字段,返回为FieldInfo类型的数组
//只能获取到公有字段
FieldInfo[] f = t.GetFields ();
foreach (var item in f)
Console.WriteLine (item);
}
(4)、GetInterface()、GetInterfaces() --> 返回InterfaceInfo类型,用于取得该类实现的接口的信息
(5)、GetMember()、GetMembers() --> 返回MemberInfo类型,用于取得该类的所有成员的信息
eg、
public static void testMember()
{
Type t = typeof(Student);
var members = t.GetMembers ();
foreach (var item in members)
Console.WriteLine (item.MemberType+":"+item);//item.MemberType,显示成员的类型
}
(6)、GetMethod()、GetMethods() --> 返回MethodInfo类型,用于 取得该类的方法的信息
eg、
public static void testMethod()
{
Type t = typeof(Student);
var array= t.GetMethods ();
foreach (var item in array)
Console.WriteLine (item);
}
(7)、GetProperty()、GetProperties() --> 返回PropertyInfo类 型,用于取得该类的属性的信息
eg、
public static void testProperty()
{
Type t = typeof(Student);
PropertyInfo[] array= t.GetProperties ();
foreach (var v in array)
Console.WriteLine (v);
}
4)、用构造方法动态生成对象
eg、
public static void CreateObject()
{
Type t = typeof(Student);
Type[] types = new Type[]{ typeof(string), typeof(int), typeof(int) };
ConstructorInfo info = t.GetConstructor (types);
object[] objects = new object[]{ "Tom", 19, 1 };
Student s = (Student)info.Invoke (objects);
s.Show ();
}
5)、用Activator生成对象
eg、
public static void testActivator()
{
//生成对象必然会调用构造函数
//没有参数调用的无参的构造
Type t = typeof(Student);
Student s1 = (Student)Activator.CreateInstance (t);
s1.Show ();
//给构造函数传参
Type t1 = typeof(Student);
Student s2 = (Student)Activator.CreateInstance (t1,"Tom",15,2);
s2.Show ();
//用object数组来给构造函数的参数传值
Type t2 = typeof(Student);
object[] objects = new object[]{ "Jack", 19, 3 };
Student s3 = (Student)Activator.CreateInstance (t2, objects);
s3.Show ();
}
4、System.Reflection.Assembly类:它可以用于访问给定程序集的信息,或者把这个程序集加载到程序中。
通过Assembly获取程序集中所有的类:
Type[] t = ass.GetTypes();
eg、通过一个exe文件,获取其源码中的内容,并调用其函数
public static void testAssembly()
{
Assembly ay = Assembly.LoadFile ("/Users/neworigin/Desktop/Day20-2测试反射.exe");//引号内为exe文件的路径
//Console.WriteLine (ay.CodeBase);//打印路径
//获取类
// Type[] types = ay.GetTypes ();
// foreach (var t1 in types)
// Console.WriteLine (t1);
object o=ay.CreateInstance("Day202测试反射.Test");//引号内为(命名空间.类名)。
Type t = o.GetType ();
MethodInfo info = t.GetMethod ("print");//引号内为调用的函数名
info.Invoke (o, null);
}