Spring是如何簡化開發(fā)的

Spring為了簡化Java開發(fā)而產(chǎn)生,使用Spring可以讓簡單的JavaBean實現(xiàn)之前只有EJB才能完成的事情,在簡單性,可測試性和松耦合等方面從Spring獲益。

一、Spring是怎么簡化java開發(fā)的??

1、 基于POJO的輕量級和最小侵入性變成
2、通過依賴注入和面向接口實現(xiàn)松耦合
3、基于切面和慣例進行聲明式編程
4、通過切面和模板減少樣板式代碼


1、Spring不會在HelloWorld上導入亂糟糟的方法。
2、依賴注入Dependency Injection(DI)
  • 為什么要用DI

因為應用之間是通過很多組件和類的相互協(xié)作來完成的。通常,每個對象負責管理與自己相互協(xié)作的對象的引用,這樣會導致高度耦合和難以測試的代碼。
也就是相互調用太多,代碼看起來太復雜。當一個組件需要修改的時候,所有涉及到它的其他組件都要進行修改。
這里講了依賴注入的方式之一,構造器注入。

   public class DamselRescuingKnight implements Knight{
   private RescueDamselQuest quest;
   public DamselRescuingKnight(){
      quest = new RescueDamselQuest();
   }
  public void embarkOnQuest() throws QuestException{
      quest.embark();
   }
}
  • DamselRescuingKnight在他的構造函數(shù)中自行創(chuàng)建了RescueDamselQuest。所以騎士就和這個任務緊密的結合在一起了。而且難以測試embark()是否在embarkQuest()方法被調用的時候執(zhí)行。所以這種寫法很不好。
  • 所以我們采用依賴注入。對象的依賴關系將由負責協(xié)調系統(tǒng)中各個對象的第三方組件在創(chuàng)建對象時設定。對象無需自行創(chuàng)建或者管理它們的依賴關系。依賴關系將被自動注入到需要它們的對象中去。
 public class BraveKnight implements Knight{
     private Quest quest;
     public BraveKnight(Quest quest){
       this.quest = quest;      -->Quest被注入進來
     }
     public void embarkOnQuest() throws QuestException{
         quest.embark();
     }
}
  • 這里沒有自行創(chuàng)建任務。而是在構造時把任務當做構造器參數(shù)傳入,即構造注入
  • 而 且Quest是所有任務的接口。可以實現(xiàn)任意一種任務。重要的是騎士沒有與任何一個特定的任務發(fā)生耦合。
  • 這樣就實現(xiàn)了松耦合。
  • 如果一個對象只通過接口(而不是具體化實現(xiàn)或者初始化的過程)來表明依賴關系,那么這種依賴就能夠在對象本身毫不知情的情況下,用不同的具體實現(xiàn)進行替換。也就是改實現(xiàn)不用換接口。
  • 可以采用mock測試

然后可以用Spring將SlayDragonQuest通過XML文件注入到BraveKnight當中。

<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
   xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
   http://www.springframework.org/schema/cache 
   default-lazy-init="true">

<bean id="knight" class = "com.springinaction.knights.BraveKnight">
<constructor-arg ref="quest"></constructor-arg>     -->通過Constructor-arg來告訴Spring額外的信息
</bean>
<bean id="quest"
  class="com.springinaction.knight.SlayDragonQusest">
</bean>
</beans>
  • Spring通過Application Context應用上下文裝載Bean

  • Spring應用上下文全權負責對象的創(chuàng)建和組裝。

  • Spring自帶了幾種應用上下文的實現(xiàn),它們之間的主要區(qū)別是如何加載它們的配置

    public class KnightMain{
       public static void main(String[] args){
            ApplicationContext context = 
                 new ClassPathXmlApplicationContext("knight.xml"); -->加載Spring上下文
            Knight knight = (Knight) context.getBean("knight");    -->獲取knight Bean
            knight.embarkOnQuest();                                -->使用knight
       }
    }
    
  • 這里的main()方法創(chuàng)建了一個Spring上下文,該上下文加載了knight.xml文件。隨后它調用該上下文獲取一個ID為knight的Bean。得到Knight的對象之后,只需要調用embarkOnQuest()方法就可以執(zhí)行所賦予的任務。

3、應用切面 (AOP Aspect Oriented Programming)

允許你把遍布應用程序各處的功能分離出來形成可重用的組件。

  • 為什么要用AOP?

因為系統(tǒng)由許多不同的組件組成,每個組件負責一塊特定的職責。有些系統(tǒng)服務跨越多個組件,被稱為橫切關注點。
如果將這些服務分散到各個組件中,代碼將會變得重復而混亂。每個模塊都要調用這些服務
所以AOP使這些服務模塊化,并以聲明的方式將他們應用到需要影響的組件中去。將他們想象成一個切面,覆蓋了多個組件。使這些組件更關注自身業(yè)務而不需要了解系統(tǒng)服務

  • 如何實現(xiàn)?
    在Spring配置文件中聲明它。
<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
   xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
   http://www.springframework.org/schema/cache 
   default-lazy-init="true">

<bean id="knight" class = "com.springinaction.knights.BraveKnight">
<constructor-arg ref="quest"></constructor-arg>
</bean>
<bean id="quest"
  class="com.springinaction.knight.SlayDragonQusest">
</bean>

<bean id="minstrel" class="com.springinaction.knights.Minstrel">              -->聲明Minstrel Bean
</bean>
<aop:config>
     <aop:aspect ref="minstrel">
          <aop:pointcut id="embark"
               expression="execution(**.embarkOnQuest(..))"/>  -->定義切面
          <aop:before pointcut-ref="embark"                    -->聲明前置通知
               method="singBeforeQuest"/>
          <aop:after pointcut-ref="embark"                     -->聲明后置通知
               method="singAfterQuest/>
     </aop:aspect>
</aop:config>
</beans>

使用AOP配置的命名空間把Minstrel Bean聲明為一個切面:

  • 先聲明Minstrel為一個Bean,然后在<aop:aspect>元素中引用該bean
    這樣就不用在knight中每次調用Minstrel了
4、使用模板消除樣板式代碼:封裝

比如使用JDBC的時候,樣板式代碼是核心業(yè)務代碼的好幾倍,這時候用Spring就簡潔的多
Spring通過模板封裝來消除樣板式代碼。比如JDBCTemplate就可以簡化原來的代碼,因為都被封裝了。

二、Bean的容器和生命周期

在基于Spring的應用中,應用對象生存于Spring的容器中。
容器是Spring框架的核心。有兩種類型

  • Bean工廠(Bean Factories)
  • 應用上下文(Application Context)基于BeanFactory之上構建,并提供面向應用的服務。最常用

三種最常見的應用上下文
1、ClassPathXmlApplicationContext
從類路徑下的XML配置文件中加載上下文定義,把應用上下文定義文件當做資源

2、FileSystemXmlApplicationContext
讀取文件系統(tǒng)下的XML配置文件并加載上下文定義

3、XmlWebApplicationContext
讀取web應用下的XML配置文件并加載上下文定義

通過現(xiàn)有的應用上下文引用,可以調用應用上下文的getBean()方法從Spring容器中獲取Bean

最后編輯于
?著作權歸作者所有,轉載或內(nèi)容合作請聯(lián)系作者
【社區(qū)內(nèi)容提示】社區(qū)部分內(nèi)容疑似由AI輔助生成,瀏覽時請結合常識與多方信息審慎甄別。
平臺聲明:文章內(nèi)容(如有圖片或視頻亦包括在內(nèi))由作者上傳并發(fā)布,文章內(nèi)容僅代表作者本人觀點,簡書系信息發(fā)布平臺,僅提供信息存儲服務。

相關閱讀更多精彩內(nèi)容

  • Spring Cloud為開發(fā)人員提供了快速構建分布式系統(tǒng)中一些常見模式的工具(例如配置管理,服務發(fā)現(xiàn),斷路器,智...
    卡卡羅2017閱讀 136,506評論 19 139
  • Spring Boot 參考指南 介紹 轉載自:https://www.gitbook.com/book/qbgb...
    毛宇鵬閱讀 47,256評論 6 342
  • 依賴注入 按照傳統(tǒng)的做法,每個對象負責管理與自己相互協(xié)作的對象的引用,這將會導致高度耦合和難以測試的代碼。例如: ...
    謝隨安閱讀 618評論 0 0
  • 買一本書 一本有趣的書 放在我辦公室的抽屜里 工作疲累 陰雨連綿的天氣里 取出來翻一翻 暫時把煩悶忘記 比如養(yǎng)一盆...
    水仙書生閱讀 344評論 0 2
  • “朝看水東流,暮看日西沉” 在時光的沉浮中,我留下了什么,又帶走了什么,仿佛一直都在遺忘中度過,不知為何,一直...
    西瓜丸子zero閱讀 302評論 0 1

友情鏈接更多精彩內(nèi)容