設(shè)計(jì)模式中定義: 為其他對(duì)象提供一種代理以控制對(duì)這個(gè)對(duì)象的訪問.
為什么要使用Proxy?
1.授權(quán)機(jī)制
我們開發(fā)一個(gè)應(yīng)用系統(tǒng)時(shí),用戶請(qǐng)求任何頁(yè)面都要經(jīng)過權(quán)限控制,最早開發(fā)的時(shí)候我們常常封裝一個(gè)權(quán)限驗(yàn)證方法,然后在每個(gè)jsp或者對(duì)應(yīng)的servlet中增加相關(guān)代碼,但是用戶對(duì)權(quán)限的需求往往是多變的,這樣一旦權(quán)限驗(yàn)證方法變化(參數(shù)變化,增加方法),如果開發(fā)的系統(tǒng)很龐大的話,有可能你就需要修改幾百個(gè)jsp頁(yè)面或者servlet代碼。
還有我們常需要判斷session是否過期,如果過期就要重新登陸系統(tǒng),如果每個(gè)頁(yè)面或者servlet都要加判斷代碼,那也是件比較痛苦的事情。
如果我們采用代理模式,增加Proxy對(duì)象,每次用戶請(qǐng)求必須通過proxy對(duì)象處理,由它專門處理相關(guān)權(quán)限控制,一旦權(quán)限需求變化了,只需要修改Proxy對(duì)象相關(guān)的實(shí)現(xiàn)方法。
2.某個(gè)客戶端不能直接操作到某個(gè)對(duì)象,但又必須和那個(gè)對(duì)象有所互動(dòng).
舉例4個(gè)具體情況:
u 一個(gè)對(duì)象,比如一幅很大的圖像,需要載入的時(shí)間很長(zhǎng)。
u 一個(gè)需要很長(zhǎng)時(shí)間才可以完成的計(jì)算結(jié)果,并且需要在它計(jì)算過程中顯示中間結(jié)果
u 一個(gè)存在于遠(yuǎn)程計(jì)算機(jī)上的對(duì)象,需要通過網(wǎng)絡(luò)載入這個(gè)遠(yuǎn)程對(duì)象則需要很長(zhǎng)時(shí)間,特別是在網(wǎng)絡(luò)傳輸高峰期。
u 一個(gè)對(duì)象只有有限的訪問權(quán)限,代理模式(Proxy)可以驗(yàn)證用戶的權(quán)限
總之原則是,對(duì)于開銷很大的對(duì)象,只有在使用它時(shí)才創(chuàng)建,這個(gè)原則可以為我們節(jié)省很多寶貴的Java內(nèi)存. 所以,有些人認(rèn)為Java耗費(fèi)資源內(nèi)存,我以為這和程序編制思路也有一定的關(guān)系.

簡(jiǎn)單實(shí)例:
import java.lang.reflect.InvocationHandler;
import java.lang.reflect.Method;
import java.lang.reflect.Proxy;
interface AnInterface {
?public void doSomething();
}
class AClass implements AnInterface {
?public void doSomething() {
??System.out.println("Inside Method AClass.doSomething()");
?}
}
class SimpleInvocationHandler implements InvocationHandler {
?public SimpleInvocationHandler(Object realSubject) {
??this.realSubject = realSubject;
?}
?public Object invoke(Object proxy, Method m, Object[] args) {
??Object result = null;
??System.out.println("Before Calling " + m.getName());
??try {
???result = m.invoke(realSubject, args);
??} catch (Exception ex) {
???System.exit(1);
??}
??System.out.println("After Calling " + m.getName());
??return result;
?}
?private Object realSubject = null;
}
public class Test {
?public static void main(String args[]) {
??AnInterface realSubject = new AClass();
??AnInterface proxy = (AnInterface) Proxy.newProxyInstance(realSubject
????.getClass().getClassLoader(), realSubject.getClass()
????.getInterfaces(), new SimpleInvocationHandler(realSubject));
??passMeAProxy(proxy);
?}
?private static void passMeAProxy(AnInterface anInterface) {
??anInterface.doSomething();
?}
}
posted on 2006-07-25 14:28
保爾任 閱讀(594)
評(píng)論(1) 編輯 收藏 所屬分類:
Design Patten