反射从字面意思理解就是通过某一个影子来实现对原物体的操作,在java里面,也是这个意思,通过
这个反射的影子来实现对实际的世界的事物的操作.那么如何来创建这个反射的影子对象了,我们使用的就是Class关键字来实现
反射也同时在Java.lang包下的。在使用的时候,必须的要导入java.lang包。下面,我们来看看Java反射的第一步,就是获取影子对象。有三种方法来获取影子对象.代码如下.
public class DemoRefaction {
public static void main(String[] args) {
//使用getclass方法来实现的,看看下面的代码,先创建对象,在调用方法
//调用。class属性来实现.
//第三种方法就是直接classname提供的静态方法来实现的。
Object obj = new Object();
Class c1 = obj.getClass();
System.out.println("c1的hascode数值为+" + c1.hashCode());
Class c2 = Object.class;
System.out.println("c2的hascode数值为+" + c2.hashCode());
//第三种方法.
try {
Class c3 = Class.forName("java.lang.Object");
System.out.println("c3的hascode数值为+" + c3.hashCode());
System.out.println("c1和c2是否相等" + c1.equals(c2));
System.out.println("c1和c2是否相等" + c1.equals(c3));
} catch (ClassNotFoundException e) {
e.printStackTrace();
}
}
}
很明显在第一种方法的缺点就是还必须要创建对象来实现,第二种方法就是调用Object基类的.class方法来实现对影子对象的创建,最后一种方法,什么都不需要,只是需要传入一个参数就是类的全名就可以了。自由度更高.在一般的开发里面我们一般使用第三种情况来实现对影子对象的创建。
假如,我们获得了影子对象,那么我们如何操作该对象,也就是获取实际对象的属性,方法,以及构造方法了。
下面我们来看看代码.
import java.lang.reflect.Constructor;
import java.lang.reflect.InvocationTargetException;
import java.lang.reflect.Method;
import java.lang.reflect.Modifier;
public class DemoTest {
public static void main(String[] args) {
try {
Class c = Class.forName("DemoTestExample");
Method ms[] = c.getDeclaredMethods();
for (Method m : ms) {
System.out.print(Modifier.toString(m.getModifiers()) + " ");
//获取方法的修饰符
//获取方法的返回的名字。
System.out.print(m.getReturnType().getSimpleName() + " ");
//获取方法的名字.
System.out.print(m.getName() + "(");
//获取参数.注意返回的就是一个Class类型的数组,注意这里的Class式大写.
Class paras[] = m.getParameterTypes();
for (int i = 0; i < paras.length; i++) {
//输出方法的参数.getSimpleName式以简化的名字的方式来去实现的。
System.out.print(paras[i].getSimpleName() + " arg ");
if (i < paras.length - 1) {
System.out.print(",");
}
}
//输出一个换行。
System.out.print(")");
//获取抛出的异常.
Class excs[] = m.getExceptionTypes();
for (int i = 0; i < excs.length; i++) {
//输出异常的名字.
System.out.println(excs[i].getSimpleName());
//如果不是最后一个异常的话.
if (i < excs.length - 1) {
System.out.println(",");
}
}
System.out.print(" ");
System.out.println("{ }");
}
try {
//调用一个无参数的构造方法getConstructor来创建一个对象.
Constructor cs = c.getConstructor();
//创建一个实例.
try {
Object obj = cs.newInstance();
Method m = c.getDeclaredMethod("add", int.class, int.class);
//当一个类里面的成员方法被修饰为私有的时候,我们如果向使用该方法的时候,必须设置权限
//如下代码。
m.setAccessible(true);
m.invoke(obj, 189, -100);
} catch (InstantiationException e) {
e.printStackTrace();
} catch (IllegalAccessException e) {
e.printStackTrace();
} catch (InvocationTargetException e) {
e.printStackTrace();
}
} catch (NoSuchMethodException e) {
e.printStackTrace();
}
//获取方法的对象.
} catch (ClassNotFoundException e) {
e.printStackTrace();
}
}
}
public class DemoTestExample {
private void add(int a, int b) {
System.out.println("a+b=" + (a + b));
}
}
代码注释的非常清楚,这里,就不再多说了。下面我们看看如何获取构造方法。来看看下面的代码.
import java.lang.reflect.Constructor;
import java.lang.reflect.InvocationTargetException;
import java.lang.reflect.Modifier;
public class GetConstructor {
//如何利用反射获取取构造方法.
public static void main(String[] args) {
try {
Class data = Class.forName("testonsture");
//利用影子对象获取所有的构造器和构造方法.
Constructor[] arr = data.getDeclaredConstructors();
for (Constructor con : arr) {
//遍历获取的所哟䣌构造器。
System.out.print(Modifier.toString(con.getModifiers()) + " ");
//获取所有构造器的修饰符.
//获取方法的名字.
System.out.print(con.getName() + " ( ");
//获取方法的参数.返回的就是一个Classs数组.
Class[] ars = con.getParameterTypes();
for (int i = 0; i < ars.length; i++) {
//获取参数的类型,以及参数的名字
System.out.print(ars[i].getSimpleName() + " args ");
if (i < ars.length - 1) {
System.out.print(",");
}
}
System.out.println(") { }");
//获取构造方法.
try {
Constructor cs = data.getConstructor();
//调用无参数的构造方法.获取哟个object对象.
try {
Object obj = cs.newInstance();
//创建一个object对象.父类调用子类的方法,就会显示子类重写的效果.
System.out.println(obj.toString());
} catch (InstantiationException e) {
e.printStackTrace();
} catch (IllegalAccessException e) {
e.printStackTrace();
} catch (InvocationTargetException e) {
e.printStackTrace();
}
} catch (NoSuchMethodException e) {
e.printStackTrace();
}
try {
Constructor cs1 = data.getConstructor(int.class,String.class,double.class);
//获取操作权限.
cs1.setAccessible(true);
try {
Object obj2= cs1.newInstance(-1,"反射","12.34");
System.out.print(obj2.toString());
} catch (InstantiationException e) {
e.printStackTrace();
} catch (IllegalAccessException e) {
e.printStackTrace();
} catch (InvocationTargetException e) {
e.printStackTrace();
}
} catch (NoSuchMethodException e) {
e.printStackTrace();
}
}
} catch (ClassNotFoundException e) {
e.printStackTrace();
}
}
}