4、JDK动态代理
1、需要动态代理的接口:
/**
* 需要动态代理的接口
*/
public interface Subject
{
/**
* 你好
*
* @param name
* @return
*/
public String SayHello(String name);
/**
* 再见
*
* @return
*/
public String SayGoodBye();
}
2、需要代理的实际对象
/**
* 实际对象
*/
public class RealSubject implements Subject
{
/**
* 你好
*
* @param name
* @return
*/
public String SayHello(String name)
{
return "hello " + name;
}
/**
* 再见
*
* @return
*/
public String SayGoodBye()
{
return " good bye ";
}
}
3、调用处理器实现类(有木有感觉这里就是传说中的AOP啊)
import java.lang.reflect.InvocationHandler;
import java.lang.reflect.Method;
/**
* 调用处理器实现类
* 每次生成动态代理类对象时都需要指定一个实现了该接口的调用处理器对象
*/
public class InvocationHandlerImpl implements InvocationHandler
{
/**
* 这个就是我们要代理的真实对象
*/
private Object subject;
/**
* 构造方法,给我们要代理的真实对象赋初值
*
* @param subject
*/
public InvocationHandlerImpl(Object subject)
{
this.subject = subject;
}
/**
* 该方法负责集中处理动态代理类上的所有方法调用。
* 调用处理器根据这三个参数进行预处理或分派到委托类实例上反射执行
*
* @param proxy 代理类实例
* @param method 被调用的方法对象
* @param args 调用参数
* @return
* @throws Throwable
*/
public Object invoke(Object proxy, Method method, Object[] args) throws Throwable
{
//在代理真实对象前我们可以添加一些自己的操作
System.out.println("在调用之前,我要干点啥呢?");
System.out.println("Method:" + method);
//当代理对象调用真实对象的方法时,其会自动的跳转到代理对象关联的handler对象的invoke方法来进行调用
Object returnValue = method.invoke(subject, args);
//在代理真实对象后我们也可以添加一些自己的操作
System.out.println("在调用之后,我要干点啥呢?");
return returnValue;
}
}
4、测试
import java.lang.reflect.InvocationHandler;
import java.lang.reflect.Proxy;
/**
* 动态代理演示
*/
public class DynamicProxyDemonstration
{
public static void main(String[] args)
{
//代理的真实对象
Subject realSubject = new RealSubject();
/**
* InvocationHandlerImpl 实现了 InvocationHandler 接口,并能实现方法调用从代理类到委托类的分派转发
* 其内部通常包含指向委托类实例的引用,用于真正执行分派转发过来的方法调用.
* 即:要代理哪个真实对象,就将该对象传进去,最后是通过该真实对象来调用其方法
*/
InvocationHandler handler = new InvocationHandlerImpl(realSubject);
ClassLoader loader = realSubject.getClass().getClassLoader();
Class[] interfaces = realSubject.getClass().getInterfaces();
/**
* 该方法用于为指定类装载器、一组接口及调用处理器生成动态代理类实例
*/
Subject subject = (Subject) Proxy.newProxyInstance(loader, interfaces, handler);
System.out.println("动态代理对象的类型:"+subject.getClass().getName());
String hello = subject.SayHello("jiankunking");
System.out.println(hello);
// String goodbye = subject.SayGoodBye();
// System.out.println(goodbye);
}
}