增強對象的功能
- 設計模式:一些通用的解決固定問題的方式
-
-
概念:
在代理模式(Proxy Pattern)中,一個類代表另一個類的功能。這種類型的設計模式屬於結構型模式。
在代理模式中,我們創建具有現有對象的對象,以便向外界提供功能接口。
- 真實對象:
- 代理對象:
- 代理模式:代理對象代理真實對象,達到增強真實對象功能的目的。
-
實現方式(此處寫的是jdk自帶的代理方式)
-
靜態代理:在一個類文件描述代理模式
-
動態代理:在內存中形成代理類
-
實現步驟:
- 代理對象和整理對象實現相同的接口
- 代理對象=
Proxy.newProxyInstance(); - 使用代理對象調用方法
- 增強方法
-
增強方式:
-
增強參數列表
-
增強返回值類型
-
增強方法體
-
-
-
-
代碼:
接口:SaleComputer.java
package cn.ytmj.filter.proxy;
public interface SaleComputer {
public String sale(double money);
void show();
}
真實類:Computer
package cn.ytmj.filter.proxy;
/**
* 真實類
*/
public class Computer implements SaleComputer{
public String sale(double money) {
System.out.println("花了"+money+"買了一台電腦");
return "電腦一台";
}
@Override
public void show() {
System.out.println("展示電腦");
}
}
代理測試:ProxyTest
package cn.ytmj.filter.proxy;
import java.lang.reflect.InvocationHandler;
import java.lang.reflect.Method;
import java.lang.reflect.Proxy;
public class ProxyTest {
public static void main(String[] args) {
//創建真實對象
final Computer computer = new Computer();
//動態代理增強computet對象
/*
三個對象
1、ClassLoader類加載器:真實對象.getClass().getClassLoader()
2、接口數組:真實對象.getClass().getInterfaces()
3、處理器:new InvocationHandler()
*/
//proxy代理對象轉換成接口
SaleComputer proxy = (SaleComputer) Proxy.newProxyInstance(computer.getClass().getClassLoader(), computer.getClass().getInterfaces(), new InvocationHandler() {
/**
* 代理邏輯編寫的方法:代理對象調用的所有方法都會觸發該方法執行
* 參數:
* @param proxy:代理對象
* @param method:代理對象調用的方法,被封裝為對象
* @param args:代理對象調用的方法時,傳遞的實際參數
* @return
* @throws Throwable
*/
@Override
public Object invoke(Object proxy, Method method, Object[] args) throws Throwable {
/* System.out.println("被調用了");
System.out.println(method.getName());
System.out.println(args[0]);*/
if (method.getName().equals("sale")) {
//1、增強參數
//判斷是不是sale對象
Double money = (Double) args[0];
money = money * 0.85;
System.out.println("專車接...");
//使用真實對象調用該方法
String o = (String) method.invoke(computer, money);
System.out.println("免費送貨...");
//2、增強返回值
return o + "和一個鼠標墊";
} else {
Object o = method.invoke(computer, args);
return o;
}
}
});
//調用方法
//proxy.show();
String sale = proxy.sale(5000);
System.out.println(sale);
}
}
