更新時(shí)間:2022-12-30 14:30:42 來(lái)源:動(dòng)力節(jié)點(diǎn) 瀏覽2097次
1.什么是SpringAop?
一般稱(chēng)為面向切面編程,用于將那些與業(yè)務(wù)無(wú)關(guān),但卻對(duì)多個(gè)對(duì)象產(chǎn)生影響的公共行為和邏輯,抽取并封裝為一個(gè)可重用的模塊,這個(gè)模塊被命名為“切面”(Aspect),減少系統(tǒng)中的重復(fù)代碼,降低了模塊間的耦合度,同時(shí)提高了系統(tǒng)的可維護(hù)性。
2.AOP的相關(guān)概念
(1)切面(Aspect): 在Spring Aop指定就是“切面類(lèi)” ,切面類(lèi)會(huì)管理著切點(diǎn)、通知。
(2)連接點(diǎn)(Join point): 連接點(diǎn)是在應(yīng)用執(zhí)行過(guò)程中能夠插入切面(Aspect)的一個(gè)點(diǎn)。這些點(diǎn)可以是調(diào)用方法時(shí),拋出異常時(shí)。它是一個(gè)虛擬的概念,例如坐地鐵的時(shí)候,每一個(gè)站都可以下車(chē),那么這每一個(gè)站都是一個(gè)接入點(diǎn)。假如一個(gè)對(duì)象中有多個(gè)方法,那么這個(gè)每一個(gè)方法就是一個(gè)連接點(diǎn)。
(3)通知(Advice): 就是需要增加到業(yè)務(wù)方法中的公共代碼, 通知有很多種類(lèi)型分別可以在需要增加的業(yè)務(wù)方法不同位置進(jìn)行執(zhí)行(前置通知、后置通知、異常通知、返回通知、環(huán)繞通知)
(4)切點(diǎn)(Pointcut): 核心方法, 結(jié)合切點(diǎn)表達(dá)式進(jìn)行實(shí)現(xiàn)
(5)目標(biāo)對(duì)象(Target Object): 指定是增強(qiáng)的對(duì)象
(6)織入(Weaving) : spring aop用的織入方式:動(dòng)態(tài)代理。 就是為目標(biāo)對(duì)象創(chuàng)建動(dòng)態(tài)代理的過(guò)程就叫織入。
核心原理:觀察所調(diào)用的方法是否符合切入點(diǎn)表達(dá)式,如果符合,則使用代理執(zhí)行增強(qiáng)方法
3.Spring通知有哪些類(lèi)型
前置通知(Before):在目標(biāo)方法被調(diào)用之前調(diào)用通知功能;
后置通知(After):在目標(biāo)方法完成之后調(diào)用通知,此時(shí)不會(huì)關(guān)心方法的輸出是什么;
返回通知(After-returning ):在目標(biāo)方法成功執(zhí)行之后調(diào)用通知;
異常通知(After-throwing):在目標(biāo)方法拋出異常后調(diào)用通知;
環(huán)繞通知(Around):通知包裹了被通知的方法,在被通知的方法調(diào)用之前和調(diào)用之后執(zhí)行自定義的行為。
4.JDK動(dòng)態(tài)代理和CGLIB動(dòng)態(tài)代理的區(qū)別
JDK動(dòng)態(tài)代理只提供接口的代理,不支持類(lèi)的代理
該代理類(lèi)是實(shí)現(xiàn)了目標(biāo)類(lèi)接口, 并且代理類(lèi)會(huì)實(shí)現(xiàn)接口所有的方法增強(qiáng)代碼。
調(diào)用時(shí) 通過(guò)代理類(lèi)先去調(diào)用處理類(lèi)進(jìn)行增強(qiáng),再通過(guò)反射的方式進(jìn)行調(diào)用目標(biāo)方法。從而實(shí)現(xiàn)AOP
如果代理類(lèi)沒(méi)有實(shí)現(xiàn) 接口,那么Spring AOP會(huì)選擇使用CGLIB來(lái)動(dòng)態(tài)代理目標(biāo)類(lèi)。
CGLIB在運(yùn)行時(shí)動(dòng)態(tài)的生成目標(biāo)類(lèi)的一個(gè)子類(lèi)。并且會(huì)重寫(xiě)父類(lèi)所有的方法增強(qiáng)代碼,調(diào)用時(shí)先通過(guò)代理類(lèi)進(jìn)行增強(qiáng),再直接調(diào)用父類(lèi)對(duì)應(yīng)的方法進(jìn)行調(diào)用目標(biāo)方法。從而實(shí)現(xiàn)AOP。
5.SpringAop的工作過(guò)程
1.Spring 創(chuàng)建IOC容器
先掃掃描包中的所有由@Service 和@Component修飾的類(lèi),并為它們創(chuàng)建對(duì)象,放在Spring IOC容器中。
2.尋找切面類(lèi)
Spring在創(chuàng)建完對(duì)象后,開(kāi)始尋找由 @Aspect 修飾的切面類(lèi)并獲取切面類(lèi)中的所有方法。
3.尋找切面類(lèi)的方法中帶有表達(dá)式的部分
接下來(lái),Spring找到所有由合法表達(dá)式修飾的方法
4.查找有相應(yīng)方法的類(lèi)
隨后,Spring檢查它所掃描到的所有類(lèi),并將上一步中找到的方法與所有類(lèi)進(jìn)行對(duì)照,找出有這個(gè)(些)方法的類(lèi)(這個(gè)類(lèi)就是被代理類(lèi))。
5.創(chuàng)建動(dòng)態(tài)對(duì)象
最后,Spring根據(jù)上一步找到的被代理類(lèi)以及切面類(lèi)創(chuàng)建動(dòng)態(tài)類(lèi)的動(dòng)態(tài)對(duì)象并放入Spring IOC容器中。
6.Spring的事務(wù)管理機(jī)制
使用AOP實(shí)現(xiàn)
編程式事務(wù)管理:這意味你通過(guò)編程的方式管理事務(wù),給你帶來(lái)極大的靈活性,但是難維護(hù)。
聲明式事務(wù)管理:這意味著你可以將業(yè)務(wù)代碼和事務(wù)管理分離,你只需用注解和XML配置來(lái)管理事務(wù)。業(yè)務(wù)層的每個(gè)方法都是一個(gè)事務(wù)(業(yè)務(wù)邏輯層不要捕獲異常)
7.Spring的事務(wù)傳播行為
| 事務(wù)傳播行為類(lèi)型 | 說(shuō)明 |
| oropagation required | 如果當(dāng)前沒(méi)有事務(wù),就新建一個(gè)事務(wù),如果已經(jīng)存在一個(gè)事務(wù)中,加入到這個(gè)事務(wù)中。這是最常見(jiàn)的選擇。 |
| propagation supports | 支持當(dāng)前事務(wù),如果當(dāng)前沒(méi)有事務(wù),就以非事務(wù)方式執(zhí)行 |
| propagation mandatory | 使用當(dāng)前的事務(wù),如果當(dāng)前沒(méi)有事務(wù),就拋出異常 |
| propagation requires new | 新建事務(wù),如果當(dāng)前存在事務(wù),把當(dāng)前事務(wù)掛起. |
| propagation not supported | 以非事務(wù)方式執(zhí)行操作,如果當(dāng)前存在事務(wù),就把當(dāng)前事務(wù)掛起 |
| propagation never | 以非事務(wù)方式執(zhí)行,如果當(dāng)前存在事務(wù),則拋出異常。 |
| propagation nested | 如果當(dāng)前存在事務(wù),則在嵌套事務(wù)內(nèi)執(zhí)行。如果當(dāng)前沒(méi)有事務(wù),則執(zhí)行與REOUIRED類(lèi)似的操作。 |
以上就是“死磕到底的aop面試題”,你能回答上來(lái)嗎?如果想要了解更多的Java面試題相關(guān)內(nèi)容,可以關(guān)注動(dòng)力節(jié)點(diǎn)Java官網(wǎng)。
相關(guān)閱讀
Java實(shí)驗(yàn)班
0基礎(chǔ) 0學(xué)費(fèi) 15天面授
Java就業(yè)班
有基礎(chǔ) 直達(dá)就業(yè)
Java夜校直播班
業(yè)余時(shí)間 高薪轉(zhuǎn)行
Java在職加薪班
工作1~3年,加薪神器
Java架構(gòu)師班
工作3~5年,晉升架構(gòu)
提交申請(qǐng)后,顧問(wèn)老師會(huì)電話與您溝通安排學(xué)習(xí)