1. 程式人生 > >asing1elife's blog

asing1elife's blog

通過使用代理可以隱藏委託類的實現,並且實現客戶與委託類之間的解耦,在不修改委託類的前提下為客戶做一些額外處理

更多精彩

型別

  1. 靜態代理 - Java 代理之靜態代理
    • 雖然具備代理的兩個優點
    • 但侷限在於執行前必須編寫好代理類
  2. 動態代理
    • 代理類在程式執行時才被建立
    • 其優勢在於可以對多個代理類進行統一處理,而不用修改每個代理類的實現

定義 InvocationHandler 介面,充當呼叫處理器

  1. java.lang.reflect.InvocationHandler 是 Java 自帶的呼叫處理器
  2. 為處於代理類和委託類之間的中間類提供實現介面
  3. 代理類作為引數 proxy 傳入
  4. 引數 method 標識具體呼叫代理類的哪個方法
  5. 引數 args 是這個代理類方法的引數
public interface InvocationHandler {
	Object invoke(Object proxy, Method method, Object[] args);
}

定義委託類,使用動態代理,委託類必須實現某個介面

public class Sell {
	void sell();

	void ad();
}

public class Vendor implements Sell {
	public void sell() {
		System.out.println
("In sell method"); } public void ad() { System.out.println("In ad method"); } }

定義中介類,其必須實現 InvocationHandler 介面

  1. 該類持有一個委託類的引用
  2. 中介類和委託類構成靜態代理,中介類充當代理類,委託類依舊是委託類
  3. 中介類和代理類構成靜態代理,中介類充當委託類,代理類依舊是代理類
  4. 所以實際上動態代理是由兩組靜態代理組成
public class DynamicProxy implements InvocationHandler {
	private Object object;
public DynamicProxy(Object object) { this.object = object; } public void invoke(Object proxy, Mehtod method, Object[] args) { System.out.println("-- before --"); Object result = method.invoke(object, args); System.out.println("-- after --"); return result; } }

動態生成代理類

  1. 通過呼叫 Proxy.newProxyInstance() 獲取代理類例項,其實現指定介面並將方法滴啊用分發到指定的呼叫處理器
  2. 該方法的宣告 public static Object newProxyInstance(ClassLoader loader, Class<?>[] interfaces, InvocationHandler h)
  3. 引數 loader 是定義了代理類的 ClassLoader
  4. 引數 interfaces 是代理類實現的介面列表
  5. 引數 h 是調動處理器
public class MainTest {
	public static void main(String[] args) {
		DynamicProxy dynamicProxy = new DynamicProxy(new Vendor());

		Sell sell = (Sell) Proxy.newProxyInstance(Sell.class.getClassLoader(), new Class[]{Sell.class}, dynamicProxy);

		sell.sell();
		sell.ad();
	}
}