代理模式是一种设计模式,简单说即是在不改变源码的情况下,实现对目标对象的功能扩展。
目标:在eat方法执行的前后增加业务逻辑
准备工作
先准备三个基础类
public interface Person {
void eat();
}
/**
* 实现了Person接口
*/
public class OnePerson implements Person{
@Override
public void eat() {
System.out.println("我吃饭了");
}
}
/**
* 未实现任何接口
*/
public class User {
public void eat(){
System.out.println("用户正在吃饭");
}
}
静态代理
优点:直观、简单、效率高
缺点:代理对象必须提前写出,如果接口层发生了变化,代理对象的代码也要进行维护
public class PersonProxy implements Person {
private Person person;
public PersonProxy(Person person) {
this.person = person;
}
@Override
public void eat() {
System.out.println("饭前先洗手");
this.person.eat();
System.out.println("饭后百步走");
}
}
public class Demo {
public static void main(String[] args) {
Person person = new PersonProxy(new OnePerson());
person.eat();
}
}
动态代理(也叫JDK代理)
缺点:至少包含一个接口
public class JDKDongTaiProxy {
public static void main(String[] args) {
Person target = new OnePerson();
Person person = (Person) Proxy.newProxyInstance(
target.getClass().getClassLoader(),
target.getClass().getInterfaces(),
new InvocationHandler() {
@Override
public Object invoke(Object proxy, Method method, Object[] args) throws Throwable {
System.out.println("饭前先洗手");
Object result = method.invoke(target, args);
System.out.println("饭后百步走");
return result;
}
});
person.eat();
}
}
Cglib代理
缺点:依赖cglib包
public class MyMethodInterceptor implements MethodInterceptor {
@Override
public Object intercept(Object o, Method method, Object[] objects, MethodProxy methodProxy) throws Throwable {
System.out.println("饭前先洗手");
Object result = methodProxy.invokeSuper(o, objects);
System.out.println("饭后百步走");
return result;
}
}
public class Demo {
public static void main(String[] args) {
// 没有实现接口
Enhancer enhancer = new Enhancer();
enhancer.setSuperclass(User.class);
enhancer.setCallback(new MyMethodInterceptor());
User user = (User) enhancer.create();
user.eat();
// 实现了接口
enhancer = new Enhancer();
enhancer.setSuperclass(OnePerson.class);
enhancer.setCallback(new MyMethodInterceptor());
Person person = (Person) enhancer.create();
person.eat();
}
}