java常用設計模式9——代理模式
阿新 • • 發佈:2018-12-04
介紹:代理模式也稱為委託模式。
定義:為其它物件提供一種代理以控制對這個物件的訪問。
程式碼舉例:
山中有一個大王,大王有一個嘍囉,大王需要巡山來保證自己的地盤不被入侵,但是大王怎麼能自己去巡山呢?所以就要嘍囉代替大王來巡山。
我們用代理模式描述這個場景
//任務
public interface Tasks {
/**
* 需要執行的任務: 巡山
*/
void PatrolTheMountain();
}
//大王
public class DaWang implements Tasks {
//大王的嘍囉
private Louluo louluo;
public DaWang(Louluo louluo) {
this.louluo = louluo;
}
@Override
public void PatrolTheMountain() {
//大王不會自己去巡山,所以讓嘍囉代替自己去
louluo.PatrolTheMountain();
}
}
//嘍囉
public class Louluo implements Tasks {
@Override
public void PatrolTheMountain() {
Log. i("LHD", "大王叫我來巡山吶~我把人間轉一轉~");
}
}
開始執行任務:
//代理模式
//構造一個嘍囉
Louluo louluo = new Louluo();
//嘍囉加入大王麾下
DaWang daWang = new DaWang(louluo);
//巡山
daWang.PatrolTheMountain();
我們構造了一個嘍囉物件,並把這個物件交給大王,大王釋出巡山命令,而在大王類內部其實是呼叫了傳進來的嘍囉物件的巡山方法,所以真正執行巡山任務的是大王的代理小嘍囉。
執行結果:
經過大王和嘍囉的不懈努力,山頭越來越大,這個時候大王的嘍囉也越來越多,這個時候大王不會再思考該讓誰去巡山,而是用手一指,隨機選一個嘍囉去巡山。這種不需要知道真正執行者是誰的情景,我們可以使用動態代理模式。
首先需要一個支援動態代理模式的大王,也就是有很多小嘍囉的大王。
public class DynamicDaWang implements InvocationHandler {
private Object object;//具體的嘍囉物件的引用
public DynamicDaWang(Object object) {
this.object = object;
}
@Override
public Object invoke(Object proxy, Method method, Object[] args) throws Throwable {
Object result = method.invoke(object, args);
return result;
}
}
可以看到,我們實現了InvocationHandler介面,並在invoke方法裡呼叫了具體的被代理的方法。這種寫法一般是固定的。
我們聲明瞭一個Object引用,這個引用將指向真正執行任務的類,也就是被代理類,而具體執行被代理類的方法則在invoke方法中執行。
開始執行任務:
//動態代理
//隨機選一個嘍囉
Tasks louluo = new Louluo();
//有很多嘍囉的大王
DynamicDaWang proxy = new DynamicDaWang(louluo);
//獲取嘍囉的ClassLoader
ClassLoader loader = louluo.getClass().getClassLoader();
//需要執行的任務
Tasks tasks = (Tasks) Proxy.newProxyInstance(loader, new Class[]{Tasks.class}, proxy);
//大王釋出命令
tasks.PatrolTheMountain();
執行結果:
使用動態代理可以不用關心代理的到底是誰,只需要實現InvocationHandler介面即可。在具體執行任務的時候再使用反射機制動態的生成代理者的物件。
也就是說,動態代理的代理物件是在程式碼執行階段才決定的。
實際專案中的使用:
我們要實現一個功能,比如播放器功能,可以使用騰訊播放器也可以使用其它的播放器,那麼我們可以使用代理模式對播放器的通用功能做一個封裝,具體使用播放器功能的時候只調用代理物件的方法,這樣在替換播放器sdk的時候可以極大的減少程式碼的修改量。
以上就是代理模式的簡單介紹啦 (#^ . ^#)