静态代理和动态代理
静态代理
- 抽象角色:定义行为
- 真实角色:行为的具体实现
- 代理角色:代理真实角色,增强真实角色
- 使用者:和代理角色打交道
抽象角色
package com.mage.staticproxy;
/**
* 抽象角色:定义行为
*/
public interface Rent {
/**
* 出租房屋
*/
void rentHouse();
}
真实角色
package com.mage.staticproxy;
/**
* 真实角色:行为的具体实现
*/
public class Host implements Rent {
@Override
public void rentHouse() {
System.out.println("两室一厅,月租五千。");
}
}
代理角色
package com.mage.staticproxy;
/**
* 代理角色:代理真实角色,增强真实角色
*/
public class StaticAgent implements Rent {
private Rent rent;
@Override
public void rentHouse() {
System.out.println("带客户看房,打扫房间。");
rent.rentHouse();
System.out.println("谈价钱,签订合同。");
}
public StaticAgent(Rent rent) {
this.rent = rent;
}
public void setRent(Rent rent) {
this.rent = rent;
}
}
调用
package com.mage.staticproxy;
/**
* 客户:与代理打交道
*/
public class Client {
public static void main(String[] args) {
Host host = new Host();// 一个房东
StaticAgent agent = new StaticAgent(host);// 代理真实角色
agent.rentHouse();
}
}
总结
使用简单,项目中如果只有个别业务需要代理类,可以使用静态代理。
动态代理
- 实现
InvocationHandler
- 通过
Proxy.newProxyInstance(通过环境内的对象拿到类加载器, 代理需要实现的接口, 一个InvocationHandler的实例)
package com.mage.dynamicproxy;
import java.lang.reflect.InvocationHandler;
import java.lang.reflect.Method;
import java.lang.reflect.Proxy;
public class DynamicAgent implements InvocationHandler {
private Object target;// 目标对象
/**
* 获取代理对象
*
* @return
*/
public Object getProxy(Object target) {
this.target = target;
return Proxy.newProxyInstance(target.getClass().getClassLoader(),
target.getClass().getInterfaces(),
this);
}
@Override
public Object invoke(Object proxy, Method method, Object[] args) throws Throwable {
System.out.println(method.getName() + " -- 方法执行前做一些处理。");
Object result = method.invoke(target, args);
for (Object arg : args) {
System.out.println("arg = " + arg);
}
System.out.println("result = " + result);
System.out.println(method.getName() + " -- " + "方法执行后做一些处理。");
return result;
}
}
调用
package com.mage.dynamicproxy;
/**
* 客户:与代理打交道
*/
public class Client {
public static void main(String[] args) {
Host host = new Host();// 一个房东
DynamicAgent agent = new DynamicAgent();
Rent rent = (Rent) agent.getProxy(host);
rent.rentHouse(5000.00D);
}
}
总结
灵活,通过反射的机制根据传入的对象获取对应的接口,创建该接口的实现类(代理类)返回给调用者。