使用代理模式的目的,往往是因为已经存在某个类和该类的对象,想在该类的部分或全部方法执行前后在执行某些代码。
代理模式分为静态代理和动态代理,动态代理的实现方式又有两种:JDK自带的动态代理,利用了反射的原理,还有一种是 cglib方式实现的代理,利用了ASM字节码织入技术。
静态代理可以利用组合或者继承的方式实现,其目的就是为了持有被代理对象的引用,进而调用被代理对象的方法。
这里我们说一下JDK的动态代理
JDK动态代理普通写法
interface IUser {
void say(String msg);
}
class User implements IUser {
@Override
public void say(String msg) {
System.out.println("user say:" + msg);
}
}
class UserProxy implements InvocationHandler {
private IUser user;
public UserProxy(IUser user) {
this.user = user;
}
public Object getUserProxy() {
return Proxy.newProxyInstance(user.getClass().getClassLoader(), user.getClass().getInterfaces(), this);
}
@Override
public Object invoke(Object proxy, Method method, Object[] args) throws Throwable {
System.out.println("方法执行之前");
Object invoke = method.invoke(user, args);
System.out.println("方法执行之后");
return invoke;
}
}
public class Main {
public static void main(String[] args) {
IUser userProxy = (IUser) new UserProxy(new User()).getUserProxy();
userProxy.say("执行中");
}
}
JDK动态代理尝试λ写法
interface IUser {
void say(String msg);
}
class User implements IUser {
@Override
public void say(String msg) {
System.out.println("user say:" + msg);
}
}
class UserProxyFactory {
public static IUser getUserProxy(IUser user) {
return (IUser) Proxy.newProxyInstance(user.getClass().getClassLoader(), user.getClass().getInterfaces(), (proxy, method, args) -> {
System.out.println("方法执行之前");
Object invoke = method.invoke(user, args);
System.out.println("方法执行之后");
return invoke;
});
}
}
public class Main {
public static void main(String[] args) {
IUser userProxy = UserProxyFactory.getUserProxy(new User());
userProxy.say("执行中");
}
}