Cglib及其基本使用

2021-09-13 03:14:05 字數 2411 閱讀 7319

cglib是乙個強大的、高效能的**生成包,它廣泛被許多aop框架使用,為他們提供方法的攔截。下圖是我網上找到的一張cglib與一些框架和語言的關係:

對此圖總結一下:

詳細請參照**模式詳解之cglib動態**:

下面演示一下cglib**示例----對類做**。首先定義乙個dao類,裡面有乙個select()方法和乙個update()方法:

再擴充套件一點點,比方說在aop中我們經常碰到的一種複雜場景是:我們想對類a的b方法使用一種攔截策略、類a的c方法使用另外一種攔截策略

如果我們想對同乙個類的兩個方法使用不同的攔截策略,例子如下:

建立乙個dao**,實現methodinterceptor介面,目標是在update()方法與select()方法呼叫前後輸出兩句話:

public class dao 

public void select()

}

intercept方法的引數名並不是原生的引數名,我做了自己的調整,幾個引數的含義為:

public class daoproxy implements methodinterceptor 

}

再定義乙個新的proxy類

public class daoanotherproxy implements methodinterceptor 

}

方法呼叫前後輸出一下開始時間與結束時間。為了實現我們的需求,實現一下callbackfilter:

public class daofilter implements callbackfilter 

return 1;}}

返回的數值表示順序,結合下面的**解釋,測試**: 

public class cglibtest );

enhancer.setcallbackfilter(new daofilter());

dao dao = (dao)enhancer.create();

dao.update();

dao.select();}}

意思是callbackfilter的accept方法返回的數值表示的是順序,順序和setcallbacks裡面proxy的順序是一致的。再解釋清楚一點,callback陣列中有三個callback,那麼:

因此,方法的執行結果為:

符合我們的預期,因為update()方法不是方法名為"select"的方法,因此返回1,返回1使用daoanotherproxy,即列印時間;select()方法是方法名為"select"的方法,因此返回0,返回0使用daoproxy,即方法呼叫前後輸出兩句話。

這裡要額外提一下,callback陣列中我特意定義了乙個noop.instance,這表示乙個空callback,即如果不想對某個方法進行攔截,可以在daofilter中返回2,具體效果可以自己嘗試一下。

如果update()方法與select()方法在建構函式中被呼叫,那麼也是會對這兩個方法進行相應的攔截的,現在我想要的是建構函式中呼叫的方法不會被攔截,那麼應該如何做?先改一下dao**,加乙個構造方法dao(),呼叫一下update()方法:

public class dao 

public void update()

public void select()

}

如果想要在建構函式中呼叫update()方法時,不攔截的話,enhancer中有乙個setinterceptduringconstruction(boolean interceptduringconstruction)方法設定為false即可,預設為true,即建構函式中呼叫方法也是會攔截的。那麼測試方法這麼寫:

public class cglibtest );

enhancer.setcallbackfilter(new daofilter());

enhancer.setinterceptduringconstruction(false);

dao dao = (dao)enhancer.create();

dao.update();

dao.select();}}

執行結果為:

Redis基本命令及其使用

redis官方 redis是一款開源的,高階的key value資料儲存。支援眾多的資料型別,string,hash,list,set,sorted set。wget tar zxvf redis 2.4.16 tar.gz cd redis 2.4.16 make 編譯之後在 redis 2.4....

解讀Flex布局及其基本使用

felx布局意為 彈性布局 主要用於為盒狀模型提供最大的靈活性。被廣泛的應用於移動端,pc端的響應式布局。首先 定義盒子為flex布局 box設定為flex布局之後,子元素的 float clear,vertical align 元素將會失效。採flex布局的元素,稱為flex容器,它的所有子元素為...

Redux基本解析及其使用和React Redux

1 統一資料管理 將所需的資料提取到state中統一進行管理。當渲染後我們希望更改狀態,封裝更改狀態的方法 dispatch 2 實現dispatch 不要直接更改狀態而是使用dispatch方法進行狀態的更改,派發乙個帶有type的屬性來進行狀態的更改,但是依然無法阻止使用者更改狀態.3 crea...