一、获取Class对象:
1、Class.forName()
2、类.class
3、对象.getClass()
注意:同一类型的Class对象是相同的。
int[] a = new int[10];
int[] b = new int[100];
int[][] c = new int[20][23];
double[] d = new double[123];
a.getClass() == b.getClass()
a.getClass() != c.getClass()
a.getClass() != d.getClass()
二:利用反射机制获得属性、方法、构造器
1、利用反射获得属性 Field类
getField() 获取公共(public)的指定属性
getFields() 获取公共(public)的所有属性
getDeclaredField() 获取声明的所有属性,包括private
getDeclaredFields()
2、利用反射获得方法 Methods类
getMethod()
getMethods()
getDeclaredMethod()
getDeclaredMethods()
3、利用反射获得构造器 Constructor 类
getConstructor()
getConstructors()
getDeclaredConstructor()
getDeclaredConstructors()
三:利用反射创建对象,操作方法、操作属性。
这三个都可以使用setAccessible(true),来访问非公共的等构造器、属性和方法
1、创建对象
newInstance() 调用无参构造器来构造对象
调用有参构造器的操作是现获得有参构造器,再利用newInstance(参数),来构建对象
2、操作方法
invoke()
3、操作方法
set()设置属性值
四:反射机制使用
1、 使用反射虽然可以使java带有一定的动态性,但也会降低程序的效率
在一些情况下使用setAccessile(true),来提高程序效率。这个方法的意思
是说该构造器、方法、属性..等是安全的,不用进行安全检查。这样既可以提高效率
又可以利用反射操作一些private..属性和方法..
2、使用反射机制读取注解:
getAnnocations()// 获得所有的注解
getAnnocation()// 获得指定注解
3、使用反射机制读取泛型:
1、获得方法参数的泛型getGenericParameterTypes()
2、获得方法返回值的泛型getGenericReturnType()
一:获取反射对象的三种方式:
package com.chen.Points;
/**
* 获取Class对象
* 1、Class.forName()
* 2、类.class
* 3、对象.getClass()
* @author Administrator
*
*/
public class GetClass {
public static void main(String[] args) throws Exception {
String path = "com.chen.Points.Student";
// 第一种
Class clazz1 = Class.forName(path);
// 第二种
Class clazz2 = String.class;
// 第三种
Class clazz3 = path.getClass();// path是一个字符串对象
// 下面要注意一下:同一种类型生成的Class对象是相同的
System.out.println(clazz2 == clazz3);// true
int[] a = new int[10];
int[] b = new int[100];
int[][] c = new int[20][23];
double[] d = new double[123];
// 输出结果前两个相同,其他都不相同
System.out.println(a.getClass().hashCode());
System.out.println(b.getClass().hashCode());
// System.out.println(a.getClass() == c.getClass());报错,非法操作,因为==两边类型不同
System.out.println(c.getClass().hashCode());
System.out.println(d.getClass().hashCode());
}
}
package com.chen.Points;
/**
* javabean
* @author Administrator
*
*/
public class Student {
private String name;
private long id;
private int age;
public Student() {
}
public Student(String name, long id, int age) {
super();
this.name = name;
this.id = id;
this.age = age;
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public long getId() {
return id;
}
public void setId(long id) {
this.id = id;
}
public int getAge() {
return age;
}
public void setAge(int age) {
this.age = age;
}
}
二:用反射获取操作构造器、方法、属性
package com.chen.Points;
import java.lang.reflect.Constructor;
import java.lang.reflect.Field;
import java.lang.reflect.Method;
/**
*
* 1、利用反射获得属性
* 2、利用反射获得方法
* 3、利用反射获得构造器
*
* 4、利用反射创建对象
* 5、利用反射调用方法
* 6、利用反射访问属性
* @author Administrator
*
*/
public class Use_Class {
static String path = "com.chen.Points.Student";
public static void main(String[] args) throws Exception {
System.out.println("test01:====================");
test01();
System.out.println("test02:=====================");
test02();
System.out.println("test03:====================");
test03();
System.out.println("test04=====================:");
test04();
System.out.println("test05=====================:");
test05();
System.out.println("test06=====================:");
test06();
}
/**
* 获取属性
* getField() 获取公共(public)的指定属性
* getFields() 获取公共(public)的所有属性
* getDeclaredField() 获取声明的所有属性,包括private
* getDeclaredFields()
* @throws Exception
*/
public static void test01() throws Exception {
Class<Student> clazz = (Class<Student>) Class.forName(path);
// 获得所有属性
Field[] fields = clazz.getDeclaredFields();
for(Field temp: fields) {
System.out.println(temp.getName());
}
// 获得指定属性
Field f = clazz.getDeclaredField("id");
System.out.println(f.getName());
System.out.println(f);
}
/**
* 获得方法,用法同上
* getMethod()
* getMethods()
* getDeclaredMethod()
* getDeclaredMethods()
* @throws Exception
*/
public static void test02() throws Exception {
Class<Student> clazz = (Class<Student>) Class.forName(path);
}
/**
* 获得构造器,用法同上
* getConstructor()
* getConstructors()
* getDeclaredConstructor()
* getDeclaredConstructors()
* @throws Exception
*/
public static void test03() throws Exception {
Class<Student> clazz = (Class<Student>) Class.forName(path);
// 注意一下获得指定的构造器
Constructor c = clazz.getDeclaredConstructor(String.class, long.class, int.class);
System.out.println(c);
}
/**
* 利用反射构建对象
* newInstance()
* setAccessible()可以用来操作private、protected、default等构造器
* @throws Exception
*/
public static void test04() throws Exception {
Class<Student> clazz = (Class<Student>) Class.forName(path);
// 调用无参构造器构建对象
Student stu = clazz.newInstance();
System.out.println(stu.getAge());
// 调用有参构造器构建对象
Constructor<Student> c = clazz.getDeclaredConstructor(String.class, long.class, int.class);
Student stu2 = c.newInstance("CHJ", 31212, 22);
System.out.println(stu2.getAge());
}
/**
* 用反射调用方法
* invoke()
* setAccessible()可以用来操作private、protected、default等方法
* @throws Exception
*/
public static void test05() throws Exception {
Class<Student> clazz = (Class<Student>) Class.forName(path);
Constructor<Student> c = clazz.getDeclaredConstructor(String.class, long.class, int.class);
Student stu2 = c.newInstance("CHJ", 31212, 22);
System.out.println(stu2.getName());
// 用反射来调用setName()方法
Method method = clazz.getDeclaredMethod("setName", String.class);// 没有参数就是null
method.invoke(stu2, "陈虹君");
System.out.println(stu2.getName());
}
/**
* 用反射操作属性
* setAccessible()可以用来操作private、protected、default等属性
* @throws Exception
*/
public static void test06() throws Exception {
Class<Student> clazz = (Class<Student>) Class.forName(path);
Constructor<Student> c = clazz.getDeclaredConstructor(String.class, long.class, int.class);
Student stu2 = c.newInstance("CHJ", 31212, 22);
System.out.println(stu2.getName());
Field f = clazz.getDeclaredField("name");
// 意思是:这个属性不需要安全检查,可以直接访问
f.setAccessible(true);// 如果缺省就会报错,因为name属性是私有变量,外部类无法操作
f.set(stu2, "laochen");
System.out.println(stu2.getName());
}
}