原文地址:http://leihuang.org/2014/12/09/proxy/
Structural 模式 如何设计物件之间的静态结构,如何完成物件之间的继承、实 现与依赖关系,这关乎着系统设计出来是否健壮(robust):像是易懂、易维护、易修改、耦合度低等等议题。Structural 模式正如其名,其分类下的模式给出了在不同场合下所适用的各种物件关系结构。
代理模式分为静态代理和动态代理.
静态代理
代理模式使你可以为一个对象创建一个代理,代替它去执行它的行为,举个例子,我们程序员找工作的时候,我们可以让猎头代替我们自己去联系公司找工作,此处的猎头就是代理,而我们则时被代理对象.
代码如下
public class StaticProxy {
public static void main(String[] args) {
// 你自己,相当于你实现了Runnable接口的类
Application me = new Me();
// 猎头代替你找工作,其实相当于Thread类
Application hunter = new HeadHunter(me);
hunter.apply();
}
}
// 要实现找工作的功能
interface Application {
public void apply();
}
// 真正要找工作的我
class Me implements Application {
@Override
public void apply() {
System.out.println("找到工作了");
}
}hexing
// 猎头,代替你找工作
class HeadHunter implements Application {
private Application apply = null;
public HeadHunter() {
}
public HeadHunter(Application application) {
this.apply = application;
}
private void before() {
System.out.println("联系你");
}
private void after() {
System.out.println("送你进合适公司");
}
@Override
public void apply() {
before();
apply.apply();
after();
}
}
动态代理模式
动态代理模式其实原理跟静态代理模式是一样的,只不过利用了反射机制使得系统更灵活.
静态代理模式只能代理特定接口下的子类,而动态代理可以代理任何类.
import java.lang.reflect.InvocationHandler;
import java.lang.reflect.Method;
import java.lang.reflect.Proxy;
public class DynamicProxy {
public static void main(String[] args) {
Application me = new Me() ;
HeadHunter head = new HeadHunter() ;
Application apply = (Application) head.newProxyInstance(me) ;
apply.applay();
}
}
interface Application {
public void applay();
}
class Me implements Application {
@Override
public void applay() {
System.out.println("面试!");
}
}
class HeadHunter implements InvocationHandler {
private Object target = null;
public Object newProxyInstance(Object target) {
this.target = target;
// 第一个参数,目标的装载器
// 第二个参数,目标接口,为每个接口生成代理
// 第三个参数,调用实现了InvocationHandler的对象,当你一调用代理,代理就会调用InvocationHandler的invoke方法
return Proxy.newProxyInstance(target.getClass().getClassLoader(),
target.getClass().getInterfaces(), this);
}
/**
* 反射,这样你可以在不知道具体的类的情况下,根据配置的参数去调用一个类的方法。在灵活编程的时候非常有用。
*/
@Override
public Object invoke(Object proxy, Method method, Object[] args)
throws Throwable {
before() ; //替你联系公司
method.invoke(target, args); //掉用目标方法--面试
after() ; //送你进公司
return null;
}
private void before(){
System.out.println("联系你");
}
private void after(){
System.out.println("送你进合适公司");
}
}