成人国产在线小视频_日韩寡妇人妻调教在线播放_色成人www永久在线观看_2018国产精品久久_亚洲欧美高清在线30p_亚洲少妇综合一区_黄色在线播放国产_亚洲另类技巧小说校园_国产主播xx日韩_a级毛片在线免费

資訊專欄INFORMATION COLUMN

Spring基于Annotation的依賴注入小結(jié)

adam1q84 / 2689人閱讀

摘要:設(shè)想在未來我們?yōu)榈臉?gòu)造函數(shù)新增字段那么上述代碼將修改為如果的初始化耗時(shí)很長,將影響構(gòu)造函數(shù)的后續(xù)初始化工作。上述在構(gòu)造函數(shù)里直接初始化的過程,屬于主動初始化依賴對象,二者耦合度高,不方便測試。調(diào)用方使用對進(jìn)行依賴注入。

  最近接觸了幾個(gè)比較大的Java項(xiàng)目,其中常常存在Bean之間的依賴,例如在某服務(wù)啟動前要初始化各類詞典,主要方式有顯式聲明Bean和隱式注解注入2種,本文著重介紹后一種。

1. 依賴注入簡介

  首先我們定義“依賴”是什么:如果在Class A中有Class B的實(shí)例,則稱A依賴B。
現(xiàn)在我們來構(gòu)造一個(gè)依賴:

public class UserDao {
    DBConnection conn;
    
    public UserDao() {
        // 先初始化數(shù)據(jù)庫連接
        conn = new DBConnection();
    }
}

上述代碼中,UserDao即對DBConnection存在依賴。但這樣構(gòu)造依賴存在如下問題:
(1) 耦合度高。設(shè)想在未來我們?yōu)?b>DBConnection的構(gòu)造函數(shù)新增字段name,那么上述代碼將修改為:
conn = new DBConnection();
conn = new DBConnection(String name);
(2) 如果DBConnection的初始化耗時(shí)很長,將影響構(gòu)造函數(shù)的后續(xù)初始化工作。

上述UserDao在構(gòu)造函數(shù)里直接初始化DBConnection的過程,屬于主動初始化依賴對象,二者耦合度高,不方便測試。如果被依賴對象事先就初始化好了,直接供給本Class調(diào)用,則稱之為依賴注入。例如上述代碼可改寫為如下:

public class UserDao {
    @Autowired  //依賴注入
    DBConnection conn;
    public UserDao() {
    }
}

要使注入生效,我們還需要在DBConnection中添加Bean標(biāo)識Component

@Component //將類標(biāo)識為Bean
public class DBConnection {
    public DBConnection() {
        init(); //初始化工作
    }
}

同時(shí),為了讓Bean的標(biāo)識被探測到,我們還需要在xml配置文件中添加自動掃描:

到此處相信讀者大致了解其注入原理:

將一些初始化詞典、數(shù)據(jù)庫連接的類添加諸如@Component的標(biāo)識,使之成為Bean。

Spring做自動掃描記錄下這些Bean。

調(diào)用方使用@Autowired對Bean進(jìn)行依賴注入。
此處我將這3步分別命名為:服務(wù)Bean化、自動掃描、依賴注入。接下來我將詳細(xì)介紹這3部分。

2. 服務(wù)Bean化

  事實(shí)上我們可以在任何情況下使用@Component標(biāo)識需要被"Bean化"的服務(wù)。但不久我們會發(fā)現(xiàn),其他更有水平的代碼里會有更多富于變化的標(biāo)識,例如:@Repository、@Service@Controller。這是怎么回事?設(shè)想我們現(xiàn)在有加載本地詞典的類A,本地詞典監(jiān)控類B,二者有明顯區(qū)別:前者的功能視數(shù)據(jù)訪問,后者則是監(jiān)控服務(wù),我們更愿意對標(biāo)識做更精細(xì)化的區(qū)分,具體如下:
  @Repository是為DAO(數(shù)據(jù)訪問)特制的聲明,將一個(gè)類聲明為Repository意味著該類主要功能是數(shù)據(jù)讀取、DB訪問。
  @Service則聲明該類為服務(wù)性質(zhì)的Bean,例如上文中的詞典監(jiān)控服務(wù),還有許多無關(guān)數(shù)據(jù)操作的功能性初始化類,都應(yīng)該被標(biāo)識為Service。
  @Controller聲明標(biāo)志著一個(gè)類是SpringWeb的MVC控制器,主要負(fù)責(zé)MVC之間的操縱。另一個(gè)類似的聲明是@RequestMapping,將URL映射為一個(gè)方法。

以上3個(gè)新的聲明均為@Component的子集,因此僅僅使用@Component也不影響后續(xù)的掃描和注入過程。但在現(xiàn)實(shí)生活中,其實(shí)只有很少的場合我們需要用到@Component,例如無法給類做清晰的定位時(shí)。

3. 注解掃描

注意到上文中的這段自動掃描,它的包名其實(shí)可以根據(jù)用戶需求做出更改。例如:現(xiàn)在我有一個(gè)判斷query是否為臟詞的服務(wù)A,它依賴注入了自動加載臟詞詞典的類B。此外,項(xiàng)目中還存在訪問數(shù)據(jù)庫的類C,但我們沒有為數(shù)據(jù)庫配置訪問信息。當(dāng)我們將注解掃描范圍設(shè)置為整個(gè)項(xiàng)目時(shí),啟動服務(wù)A將產(chǎn)生問題。

解決方案是縮小自動掃描范圍,使得Spring僅掃描B而不掃描C。具體做法是增加掃描過濾器, Spring支持正則Regex和AspectJ兩種表達(dá)式的方式進(jìn)行掃描過濾。
例如:


    
    

上面的xml配置就成功的掃描名為com.example.service.dictionary的package而忽略了以org.example.service.db為前綴的package。

4. 依賴注入

@Autowired:負(fù)責(zé)自動裝配被成功掃描的Bean。
@Qualifier("xxxxx"): 有時(shí)候我們有參數(shù)不同的兩個(gè)相同類的bean需要裝配(具體為什么會存在這種現(xiàn)象?可想象要連接2個(gè)數(shù)據(jù)庫。),那么如何多帶帶指定我需要裝配哪一個(gè)呢?@Qualifier配合@Autowired可用于消除這類歧義。

在方法內(nèi)部,我們也有一些"注解":
@PostConstruct@PreDestroy是Bean內(nèi)分別執(zhí)行初始化和銷毀bean的注解。b>注意!它并不屬于Spring,而是屬于J2ee里的jar包,因此使用時(shí)需要在xml配置:

@PostConstruct: 初始化bean
@preDestroy: 結(jié)束前清理。

文章版權(quán)歸作者所有,未經(jīng)允許請勿轉(zhuǎn)載,若此文章存在違規(guī)行為,您可以聯(lián)系管理員刪除。

轉(zhuǎn)載請注明本文地址:http://systransis.cn/yun/67467.html

相關(guān)文章

  • 慕課網(wǎng)_《使用Google Guice實(shí)現(xiàn)依賴注入》學(xué)習(xí)總結(jié)

    摘要:時(shí)間年月日星期六說明本文部分內(nèi)容均來自慕課網(wǎng)。慕課網(wǎng)教學(xué)源碼學(xué)習(xí)源碼第一章課程介紹課程簡介是啥讀音是輕量級的依賴注入框架說明一個(gè)的框架需要有基礎(chǔ)什么是剝離注入輕量級代碼少易維護(hù)性能優(yōu)異,跟比較。 時(shí)間:2017年10月14日星期六說明:本文部分內(nèi)容均來自慕課網(wǎng)。@慕課網(wǎng):http://www.imooc.com 教學(xué)源碼:https://github.com/zccodere/s......

    2450184176 評論0 收藏0
  • 手寫Spring之DI依賴注入

    摘要:如感興趣,可移步手寫之基于動態(tài)創(chuàng)建對象手寫之基于注解動態(tài)創(chuàng)建對象今天將詳細(xì)介紹如何手寫依賴注入,在運(yùn)行過程中如何動態(tài)地為對象的屬性賦值。完成后在中會有相關(guān)的包出現(xiàn)進(jìn)行注入前需要創(chuàng)建工廠,在運(yùn)行時(shí)從工廠中取出對象為屬性賦值。 前兩篇文章介紹了關(guān)于手寫Spring IOC控制反轉(zhuǎn),由Spring工廠在運(yùn)行過程中動態(tài)地創(chuàng)建對象的兩種方式。如感興趣,可移步: 手寫Spring之IOC基于xml...

    Cruise_Chan 評論0 收藏0
  • Spring核心 面向切面 AOP

    摘要:下圖展示了這些概念的關(guān)聯(lián)方式通知切面的工作被稱為通知。切面在指定的連接點(diǎn)被織入到目標(biāo)對象中。該注解表明不僅僅是一個(gè),還是一個(gè)切面。 在軟件開發(fā)中,散布于應(yīng)用中多處的功能被稱為橫切關(guān)注點(diǎn)(crosscutting concern)。通常來講,這些橫切關(guān)注點(diǎn)從概念上是與應(yīng)用的業(yè)務(wù)邏輯相分離的(但是往往會直接嵌入到應(yīng)用的業(yè)務(wù)邏輯之中)。把這些橫切關(guān)注點(diǎn)與業(yè)務(wù)邏輯相分離正是面向切面編程(AOP...

    Winer 評論0 收藏0
  • 第一章--Spring之旅

    摘要:兩種方式來表示的應(yīng)用上下文。日志,事務(wù)管理和安全這樣的系統(tǒng)服務(wù)經(jīng)常融入到具有核心業(yè)務(wù)邏輯的組件中去,這些系統(tǒng)服務(wù)通過被稱為橫切關(guān)注點(diǎn)。容器使用管理構(gòu)成應(yīng)用的組件,他會創(chuàng)建相互協(xié)作的組件之間的關(guān)聯(lián)。的生命周期四俯瞰的風(fēng)景線模塊,,,, 完整代碼請見:https://github.com/codercuixi...為了降低Java開發(fā)的復(fù)雜性,Spring采用了以下4種策略: 基于poj...

    pkwenda 評論0 收藏0
  • SpringBoot基礎(chǔ)篇AOP之基本使用姿勢小結(jié)

    摘要:通知和切點(diǎn)共同定義了關(guān)于切面的全部內(nèi)容,它是什么時(shí)候,在何時(shí)和何處完成功能引入允許我們向現(xiàn)有的類添加新的方法或者屬性組裝方面來創(chuàng)建一個(gè)被通知對象。這可以在編譯時(shí)完成例如使用編譯器,也可以在運(yùn)行時(shí)完成。和其他純框架一樣,在運(yùn)行時(shí)完成織入。 原文:190301-SpringBoot基礎(chǔ)篇AOP之基本使用姿勢小結(jié) 一般來講,談到Spring的特性,繞不過去的就是DI(依賴注入)和AOP(切...

    timger 評論0 收藏0

發(fā)表評論

0條評論

最新活動
閱讀需要支付1元查看
<