代理模式是Spring的AOP模式中实现的机制
1、静态代理
角色分析
- 抽象角色:一般用接口或者抽象类
- 真实对象:被代理的角色
- 代理角色:代理真实角色,代理真实角色后并且会带上一些附属操作
- 客户:访问代理角色的人
这里使用一个租房的例子来说明静态代理
抽象角色
public interface Rent {
//出租房子
void Rent();
}
真实对象
public class Host implements Rent{
@Override
public void Rent() {
System.out.println("房东要出租房子!");
}
}
代理角色
public class Proxy implements Rent{
private Host host;
public Proxy() {
}
public Proxy(Host host) {
this.host = host;
}
@Override//代理商和房东的共同目标
public void Rent() {
seeHouse();
host.Rent();
fare();
}
public void fare(){
System.out.println("代理帮忙收房租");
}
public void seeHouse(){
System.out.println("代理商带你看房子");
}
}
客户
public class Client {
public static void main(String[] args) {
Proxy proxy = new Proxy(new Host());
proxy.Rent();
}
}
2、动态代理
抽象角色
public interface Rent {
//出租房子
void Rent();
//seeHello
void seeHello();
}
真实对象
public class Host implements Rent {
@Override
public void Rent() {
System.out.println("房东要出租房子!");
}
@Override
public void seeHello() {
System.out.println("对租客说hello");
}
}
这里的代理角色是由反射创建出来的
//利用这个类,等下生成代理类
public class ProxyInvacationHandler implements InvocationHandler {
//被代理的接口
private Rent rent;
public void setRent(Rent rent) {
this.rent = rent;
}
//生成得到代理类
public Object getProxy(){
return Proxy.newProxyInstance(this.getClass().getClassLoader(),rent.getClass().getInterfaces(),this);
}
//invoke的作用是返回调用接口方法的值
@Override
public Object invoke(Object proxy, Method method, Object[] args) throws Throwable {
//利用反射返回接口方法的结果
Object invoke = method.invoke(rent, args);
seeHouse();
return invoke;
}
public void seeHouse(){
System.out.println("中介带顾客去看房子");
}
}
客户
public class Client {
public static void main(String[] args) {
//真实角色
Host host = new Host();
ProxyInvacationHandler pih = new ProxyInvacationHandler();
//通过调用处理角色来处理我们要使用的接口对象
pih.setRent(host);
//通过生成得到代理类(也就是getProxy方法)得到代理类对象
Rent proxy = (Rent) pih.getProxy();
//代理类对象方法的返回值,是交给 ProxyInvacationHandler中的invoke来传递的
proxy.Rent();
proxy.seeHello();
}
}
代理模式的好处:
1.可以使真实对象更专注于业务编写,不用去关注公共业务
2,公共业务交给代理角色去集中处理,实现了业务分工