java设计模式之代理模式
静态代理
静态代理实现过程概述:
- 定义接口,这是一个代理类与被代理类都实现的接口
- 定义被代理类,实现共同接口,实现接口方法
- 定义代理类,实现共同接口,实现接口方法,方法内调用被代理类同名方法
- 以被代理对象为参数,构建代理人对象
- 代理人对象执行实现的接口方法
// 1.定义接口,这是一个代理类与被代理类都实现的接口
interface Buyer{
public void buy();
}
// 2.被代理类,实际需求人
class Principal implements Buyer{
private String name;
public Principal(String name) {
this.name = name;
}
// 实现接口的核心方法,被代理的动作
@Override
public void buy() {
System.out.println("被代理人买房子");
}
}
// 3.代理类,实现共同接口
class Agent implements Buyer{
// 定义一个对象,共同接口实现后的对象(实际上是被代理类对象)
private Buyer buyer;
// 构造器,参数为被代理类对象
public Agent(Buyer buyer) {
this.buyer = buyer;
}
// 实现接口的方法,内部调用被代理类的实现的接口的方法
@Override
public void buy() {
findHouse();
buyer.buy();
}
// 代理类其他操作
public void findHouse(){
System.out.println("帮被代理人找房子");
}
}
class JavaStudy {
public static void main(String[] args) {
Principal principal = new Principal("李华"); // 定义被代理人对象
Agent agent = new Agent(principal); // 代理人对象,以被代理人对象为参数
agent.buy(); // 代理人执行动作,实际上执行的被代理人内部的核心方法,代理人可以扩展
}
}
动态代理
动态代理实现过程概述:
- 定义被代理类,并实现相应接口
- 定义代理类工厂,核心方法返回代理类对象
- 被代理类对象做且此代理类工厂方法的参数,产生代理类对象,执行被代理类的方法
import java.io.Serializable;
import java.lang.reflect.InvocationHandler;
import java.lang.reflect.Method;
import java.lang.reflect.Proxy;
// 1.定义接口,这是一个代理类与被代理类都实现的接口
interface Buyer{
void buy(int money);
}
interface Happiness{
String getFeeling();
};
// 2.被代理类1,实际需求者
class Principal implements Buyer{
private String name;
public Principal(String name) {
this.name = name;
}
public String getName() {
return name;
}
// 实现接口的核心方法,被代理的动作
@Override
public void buy(int money) {
System.out.println("被代理人用"+money+"万元买房子");
}
}
// 3.被代理类2,实际需求者
class HappyBoy implements Happiness {
private String name;
public HappyBoy(String name) {
this.name = name;
}
public String getName() {
return name;
}
// 实现接口的核心方法,被代理的动作
@Override
public String getFeeling() {
return "I am very happy";
}
}
// 代理类工厂
class ProxyFactory {
// 此方法根据被代理类返回一个代理类的对象
public static Object getProxyInstance(Object obj){ // 参数为被代理类对象
MyInvocationHandler myInvocationHandler = new MyInvocationHandler();
myInvocationHandler.bind(obj);
//返回实现了obj实现的接口的代理类对象,参数(被代理类的类加载器,被代理类实现的接口,一个绑定被代理类的可调用其方法的处理器)
return Proxy.newProxyInstance(obj.getClass().getClassLoader(),obj.getClass().getInterfaces(), myInvocationHandler);
};
}
class MyInvocationHandler implements InvocationHandler{
private Object obj; // 被代理类对象
public void bind(Object obj){ // 将被代理类对象与MyInvocationHandler实例绑定
this.obj = obj;
}
@Override
public Object invoke(Object o, Method method, Object[] objects) throws Throwable {
Object res = method.invoke(obj, objects); // method即为代理的方法,obj为被代理类
return res;
}
};
class JavaStudy {
public static void main(String[] args) {
Principal principal = new Principal("李华"); // 定义被代理人对象
// 因为代理类对象实现了被代理类对象的接口,所以可以强转(Buyer为共同接口)
Buyer proxyInstance = (Buyer) ProxyFactory.getProxyInstance(principal); // principal的代理类对象
System.out.print(principal.getName()+"--");
proxyInstance.buy(100);
HappyBoy happyBoy = new HappyBoy("张三");// 定义被代理人对象
// 因为代理类对象实现了被代理类对象的接口,所以可以强转(Happiness为共同接口)
Happiness proxyInstance2 = (Happiness) ProxyFactory.getProxyInstance(happyBoy); // principal的代理类对象
System.out.println(happyBoy.getName()+"--"+proxyInstance2.getFeeling());
}
}
// 输出:
李华--被代理人用100万元买房子
张三--I am very happy