JDK动态代理是一种常用的设计模式。
动态代理实现步骤:
1、首先创建一个实现InvocationHandler
接口的类,它必须实现invoke
方法,在invoke
方法中来添加具体的业务逻辑:
public class TimeHandler implements InvocationHandler {
public TimeHandler(Object object) {
super();
this.object = object;
}
private Object object;
/**
*
* @param proxy 被代理对象
* @param method 被代理对象的方法
* @param args 方法的参数
* @return 返回值是Object 也就是方法的返回值
* @throws Throwable
*/
@Override
public Object invoke(Object proxy, Method method, Object[] args) throws Throwable {
long starttime = System.currentTimeMillis();
System.out.println("汽车开始行驶...");
method.invoke(object);
long endtime = System.currentTimeMillis();
System.out.println("汽车结束行驶...");
System.out.println("汽车行驶时间:" + (endtime - starttime) + "毫秒");
return null;
}
}
2、创建被代理的类以及接口。
被代理接口:
public interface Moveable {
//增加一个行驶的接口
void move();
}
被代理类:
public class Car implements Moveable{
@Override
public void move() {
//实现开车,开车时间为1秒钟
try {
Thread.sleep(new Random().nextInt(1000));
} catch (InterruptedException e) {
e.printStackTrace();
}
}
}
3、调用Proxy
的静态方法,创建一个代理类。
/**
* 动态代理测试类
*/
public class Test {
public static void main(String[] args) {
//引入Car类,也就是被代理的类,他也实现了一个接口
Car car = new Car();
InvocationHandler h = new TimeHandler(car);
//得到car的class
Class<?> cls = car.getClass();
//
/**
* 采用动态代理,来生成我们的代理类,返回的对象就是动态代理对象
* cls.getClassLoader() 类加载器
* cls.getInterfaces() 实现接口
* h 实现的处理器 InvocationHandler
*/
Moveable m = (Moveable) Proxy.newProxyInstance(cls.getClassLoader(),
cls.getInterfaces(),h);
//通过代理调用接口
m.move();
}
}
4、通过代理调用方法。
//通过代理调用接口,第三步骤已经写出
m.move();
最后的输出结果:
汽车开始行驶...
汽车结束行驶...
汽车行驶时间:350毫秒
小结:
JDK代理只能代理实现了接口的类,没有实现接口的类是不能代理的。
但是CGLIB动态代理是针对类来实现代理的。