代理模式是給一個(gè)對象提供一個(gè)代理,以控制對它的訪(fǎng)問(wèn),如只有授權用戶(hù)才可以訪(fǎng)問(wèn)某個(gè)對象,給對象添加日志功能。
動(dòng)態(tài)代理是提供運行時(shí)實(shí)現代理模式的一種方法。
被代理對象 |
代理產(chǎn)生器 |
代理對象 |
使用代理的對象 |
如上圖所示,當要用到代理對象時(shí),需調用代理產(chǎn)生器創(chuàng )建一個(gè)代理類(lèi)來(lái)控制被代理的對象。
代理產(chǎn)生器的功能在JDK中也就是通過(guò)Proxy.newProxyInstance來(lái)動(dòng)態(tài)創(chuàng )建一個(gè)代理類(lèi)。
假設有一個(gè)CarCompany接口,他具備制造汽車(chē)的功能makeCar();不同的廠(chǎng)商有不同的makeCar的實(shí)現?,F在通過(guò)動(dòng)態(tài)代理來(lái)添加一個(gè)測試makeCar所消耗時(shí)間的功能。
1. CarCompany.java
Interface CarCompay{
Public void makeCar();
}
2. CarCompanyA.java
public class CarCompanyA implements CarCompany {
public void makeCar() {
System.out.println("Company A make a car!");
}
}
3. CarCompanyHandler.java
Public class CarCompany implements CarCompany{
CarCompany com;
public CarCompanyHandler(CarCompany a){
this.com = a;
}
public Object invoke(Object proxy, Method method, Object[] args)
throws Throwable {
if(method.getName().equals("makeCar")){
System.out.println("time1:" + System.currentTimeMillis());
method.invoke(this.com,new Class[]{});
System.out.println("time2:" + System.currentTimeMillis());
}
return null;
}
}
4. Test.java
Public class Test{
Public static void main(String[] arg){
CarCompanyA a = new CarCompanyA();
CarCompanyHandler handler = new CarCompanyHandler(a);
//產(chǎn)生一個(gè)新的代理類(lèi)
CarCompany com = (CarCompany) Proxy.newProxyInstance(Test.class
.getClassLoader(), new Class[] { CarCompany.class }, handler);
com.makeCar();
}
}
5. 代理產(chǎn)生器動(dòng)態(tài)生成的類(lèi)(Proxy.newProxyInstance產(chǎn)生的)
相信看了如下代碼后就會(huì )很清楚動(dòng)態(tài)代理的執行過(guò)程。
public final class XXXXX$proxy extends Proxy
implements CarCompany
{
public final void makeCar()
{
try
{
//調用InvocationHandler的invoke方法
super.h.invoke(this, m3, null);
return;
}
catch(Error _ex) { }
catch(Throwable throwable)
{
throw new UndeclaredThrowableException(throwable);
}
}
private static Method m3;
static
{
try
{
m3 = Class.forName("com.home.CarCompany").getMethod("makeCar", new Class[0]);
}
catch(NoSuchMethodException nosuchmethodexception)
{
throw new NoSuchMethodError(nosuchmethodexception.getMessage());
}
catch(ClassNotFoundException classnotfoundexception)
{
throw new NoClassDefFoundError(classnotfoundexception.getMessage());
}
}
public a$proxy(InvocationHandler invocationhandler)
{
super(invocationhandler);
}
}
聯(lián)系客服