作者:張豐哲
創(chuàng)新互聯(lián)建站服務(wù)項(xiàng)目包括會(huì)寧網(wǎng)站建設(shè)、會(huì)寧網(wǎng)站制作、會(huì)寧網(wǎng)頁(yè)制作以及會(huì)寧網(wǎng)絡(luò)營(yíng)銷(xiāo)策劃等。多年來(lái),我們專(zhuān)注于互聯(lián)網(wǎng)行業(yè),利用自身積累的技術(shù)優(yōu)勢(shì)、行業(yè)經(jīng)驗(yàn)、深度合作伙伴關(guān)系等,向廣大中小型企業(yè)、政府機(jī)構(gòu)等提供互聯(lián)網(wǎng)行業(yè)的解決方案,會(huì)寧網(wǎng)站推廣取得了明顯的社會(huì)效益與經(jīng)濟(jì)效益。目前,我們服務(wù)的客戶(hù)以成都為中心已經(jīng)輻射到會(huì)寧省份的部分城市,未來(lái)相信會(huì)繼續(xù)擴(kuò)大服務(wù)區(qū)域并繼續(xù)獲得客戶(hù)的支持與信任!
原文:https://www.jianshu.com/p/58759fef38b8
在Java領(lǐng)域,動(dòng)態(tài)代理應(yīng)用非常廣泛,特別是流行的Spring/MyBatis等框架。JDK本身是有實(shí)現(xiàn)動(dòng)態(tài)代理技術(shù)的,不過(guò)要求被代理的類(lèi)必須實(shí)現(xiàn)接口,不過(guò)cglib對(duì)這一不足進(jìn)行了有效補(bǔ)充。本篇博客將涉及2個(gè)話(huà)題:第一,JDK動(dòng)態(tài)代理的實(shí)現(xiàn)原理,帶你探索動(dòng)態(tài)代理的實(shí)質(zhì)面目;第二,自己動(dòng)手寫(xiě)代碼去實(shí)現(xiàn)JDK動(dòng)態(tài)代理,去創(chuàng)造世界!
先寫(xiě)一個(gè)例子,感性認(rèn)識(shí)下動(dòng)態(tài)代理~
業(yè)務(wù)接口:
interface
業(yè)務(wù)實(shí)現(xiàn)類(lèi):
interface impl
業(yè)務(wù)處理類(lèi):
Handler
測(cè)試類(lèi):
test
運(yùn)行結(jié)果:
result
在JDK動(dòng)態(tài)代理中涉及如下角色:
業(yè)務(wù)接口Interface、業(yè)務(wù)實(shí)現(xiàn)類(lèi)target、業(yè)務(wù)處理類(lèi)Handler、JVM在內(nèi)存中生成的動(dòng)態(tài)代理類(lèi)$Proxy0
動(dòng)態(tài)代理原理圖:
動(dòng)態(tài)代理的真實(shí)面目
說(shuō)白了,動(dòng)態(tài)代理的過(guò)程是這樣的:
第一:Proxy通過(guò)傳遞給它的參數(shù)(interfaces/invocationHandler)生成代理類(lèi)$Proxy0;
第二:Proxy通過(guò)傳遞給它的參數(shù)(ClassLoader)來(lái)加載生成的代理類(lèi)$Proxy0的字節(jié)碼文件;
我們來(lái)看看上面例子中生成的$Proxy0的模樣:
$Proxy0
首先,$Proxy是實(shí)現(xiàn)了我們的業(yè)務(wù)接口(Man)的,所以客戶(hù)端顯然可以調(diào)用業(yè)務(wù)接口的方法。
其次,注意到$Proxy是繼承自Proxy,并通過(guò)構(gòu)造方法將業(yè)務(wù)處理類(lèi)傳入給父類(lèi)Proxy進(jìn)行初始化。(實(shí)質(zhì)上,你可以看看源碼,在Proxy中存在protected InvocationHandler h;)
初始化Proxy
findObject
很明顯,我們看到了業(yè)務(wù)接口的方法是如何被調(diào)用的:
最終都是回調(diào)業(yè)務(wù)處理類(lèi)(具體的Handler)的invoke方法完成調(diào)用!
在上面,我們已經(jīng)分析了JDK動(dòng)態(tài)代理的整個(gè)調(diào)用過(guò)程,接下來(lái),我們就來(lái)手寫(xiě)實(shí)現(xiàn)它吧!
先來(lái)看一眼圖:
手寫(xiě)實(shí)現(xiàn)JDK動(dòng)態(tài)代理
自定義InvocationHandler:
MyInvocationHandler
實(shí)現(xiàn)MyInvocationHandler的業(yè)務(wù)處理Handler:
MyHandler
自定義類(lèi)加載器MyClassLoader:
MyClassLoader
為什么要定義一個(gè)自定義的類(lèi)加載器呢?它的作用是什么呢?
要知道,我們是想手寫(xiě)JDK動(dòng)態(tài)代理,那么我們將自己在內(nèi)存中生成動(dòng)態(tài)代理類(lèi),那么我們?nèi)绾渭虞d呢?這時(shí)候,就可以利用自定義的類(lèi)加載器做到!
上述代碼,重寫(xiě)了findClass方法,就是為了在指定路徑下加載指定的字節(jié)碼文件。
自定義MyProxy:
MyProxy
MyProxy的作用就相當(dāng)于JDK的Proxy。MyProxy做了哪些事情呢?
第一:需要根據(jù)interfaces接口構(gòu)造出動(dòng)態(tài)代理類(lèi)需要的方法。(其實(shí)就是利用反射獲?。?/strong>
第二:把動(dòng)態(tài)生成的代理類(lèi)(即.java文件)進(jìn)行編譯,生成字節(jié)碼文件(即.class文件),然后利用類(lèi)加載進(jìn)行加載
第三:動(dòng)態(tài)代理類(lèi)進(jìn)行加載后,利用反射機(jī)制,通過(guò)構(gòu)造方法進(jìn)行實(shí)例化,并在實(shí)例化時(shí),初始化業(yè)務(wù)Hanlder
看一下MyProxy的其他方法:
編譯方法
getMethodString方法
運(yùn)行結(jié)果
我們來(lái)看一眼生成的$MyProxy0:
$MyProxy0
OK,到這里,整個(gè)JDK的動(dòng)態(tài)代理的實(shí)現(xiàn)原理以及手寫(xiě)實(shí)現(xiàn)就結(jié)束了,你學(xué)到了么?
當(dāng)前題目:純手寫(xiě)實(shí)現(xiàn)JDK動(dòng)態(tài)代理
本文來(lái)源:http://jinyejixie.com/article22/pdcocc.html
成都網(wǎng)站建設(shè)公司_創(chuàng)新互聯(lián),為您提供App開(kāi)發(fā)、品牌網(wǎng)站建設(shè)、網(wǎng)站內(nèi)鏈、小程序開(kāi)發(fā)、手機(jī)網(wǎng)站建設(shè)、品牌網(wǎng)站設(shè)計(jì)
聲明:本網(wǎng)站發(fā)布的內(nèi)容(圖片、視頻和文字)以用戶(hù)投稿、用戶(hù)轉(zhuǎn)載內(nèi)容為主,如果涉及侵權(quán)請(qǐng)盡快告知,我們將會(huì)在第一時(shí)間刪除。文章觀點(diǎn)不代表本網(wǎng)站立場(chǎng),如需處理請(qǐng)聯(lián)系客服。電話(huà):028-86922220;郵箱:631063699@qq.com。內(nèi)容未經(jīng)允許不得轉(zhuǎn)載,或轉(zhuǎn)載時(shí)需注明來(lái)源: 創(chuàng)新互聯(lián)