1. 程式人生 > >Spring IoC 容器和 bean 物件

Spring IoC 容器和 bean 物件


  • 程式的耦合性:

    耦合性(Coupling),又叫耦合度,是對模組間關聯程度的度量。耦合的強弱取決於模組間介面的複雜性、呼叫模組的方式以及通過介面傳送資料的多少。模組間的耦合度是指模組之間的依賴關係,包括控制關係、呼叫關 系、資料傳遞關係。模組間聯絡越多,其耦合性越強,同時表明其獨立性越差( 降低耦合性,可以提高其獨立 性)。

  • I o C容器

    IoCInversion of Control的縮寫,即控制反轉的意思,是解決程式耦合性的一種思想。通常建立物件的時候使用new關鍵字,控制權由程式設計師控制,而"控制反轉"是指new例項工作不由程式設計師來做而是交給Spring容器來做。解決程式耦合性的辦法有很多,而依賴注入(DI)這一功能就是IOC思想的一種具體實現

  • Spring pom.xml配置:

    <dependencies>
            <dependency>
                <groupId>org.springframework</groupId>
                <artifactId>spring-context</artifactId>
                <version>5.2.0.RELEASE</version>
            </dependency>
    </dependencies>
  • Spring 專案結構依賴:

  • Spring bean.xml的配置:

    <?xml version="1.0" encoding="UTF-8"?>
    <beans xmlns="http://www.springframework.org/schema/beans"
           xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
           xsi:schemaLocation="http://www.springframework.org/schema/beans
            http://www.springframework.org/schema/beans/spring-beans.xsd">
    
      //id 是自己定義的一個名字,相當於取一個別名 ,class是需要訪問實現類的全限定類名
        <bean id="daoService" class="com.Test.Dao.DaoServiceImpl"></bean>
      <bean id="userService" class="com.Test.Service.UserServiceImpl"></bean>
    </beans>
  • 入門案例:

    import com.Test.Dao.DaoService;
    import com.Test.Service.UserService;
    import org.springframework.context.ApplicationContext;
    import org.springframework.context.support.ClassPathXmlApplicationContext;
    
    public class MyTest {
    
        public static void main(String[] args){
    
            ApplicationContext context = new ClassPathXmlApplicationContext("bean.xml");
            //daoService,userService就是之前bean.xml檔案裡的id
            DaoService dao = (DaoService)context.getBean("daoService");
            UserService user = (UserService)context.getBean("userService");
    
            System.out.println(dao);
            System.out.println(user);
    
        }
    }

    Application Context 是 spring 中較高階的容器,它採用立即載入的策略。而BeanFactory是採用延遲載入的策略,但是也可以載入配置檔案中定義的 bean,將所有的 bean 集中在一起,當有請求的時候分配 bean。ApplicationContext包含 BeanFactory所有的功能,一般情況下,相對於 BeanFactoryApplicationContext會更加優秀。

  • ApplicationContext的三個實現類:

    1.ClassXmlPathApplicationContext:載入類路徑下的配置檔案,不需要提供 XML 檔案 的完整路徑,只需正確配置 CLASSPATH 環境變數即可,因為,容器會從CLASSPATH 中搜索 bean 配置檔案。

    2.FileSystemXmlApplicationContext:載入磁碟任意路徑下的配置檔案。

    3.AnnotationConfingApplictionContext:用於讀取註解建立容器。


  • 建立bean的三種方式:

    1.使用預設建構函式建立:

     <bean id="daoService" class="com.Test.Dao.DaoServiceImpl"></bean>

    2.(使用別人建立好的類時)使用普通工廠中的方法建立物件(或使用某個類中的方法建立物件):

    import com.Test.Service.UserService;
    import com.Test.Service.UserServiceImpl;
    
    public class InstanceFactory {
        public UserService getUserService(){
            return new UserServiceImpl();
        }
    }

    bean配置:

    <bean id="userService" factory-bean="instanceFactory" factory-method="getUserService">

    3.使用工廠中的靜態方法建立bean物件:

    import com.Test.Service.UserService;
    import com.Test.Service.UserServiceImpl;
    
    public class InstanceFactory {
        public static UserService getUserService(){
            return new UserServiceImpl();
        }
    }
    <bean id="userService" class="com.Test.Factory.StaticInstanceFactory" factory-method="getUserService"></bean>
  • bean的作用域:

當在 Spring 中定義一個 bean 時,你必須宣告該 bean 的作用域的選項。例如,為了強制 Spring 在每次需要時都產生一個新的 bean 例項,你應該宣告 bean 的作用域的屬性為 prototype。同理,如果你想讓 Spring 在每次需要時都返回同一個bean例項,你應該宣告 bean 的作用域的屬性為 singleton。

Spring 框架支援以下五個作用域,分別為singleton、prototype、request、session和global session,5種作用域說明如下所示,

注意,如果你使用 web-aware ApplicationContext 時,其中三個是可用的。

作用域 描述
singleton 在spring IoC容器僅存在一個Bean例項,Bean以單例方式存在,預設值
prototype 每次從容器中呼叫Bean時,都返回一個新的例項,即每次呼叫getBean()時,相當於執行newXxxBean()
request 每次HTTP請求都會建立一個新的Bean,該作用域僅適用於WebApplicationContext環境
session 同一個HTTP Session共享一個Bean,不同Session使用不同的Bean,僅適用於WebApplicationContext環境
global-session 一般用於Portlet應用環境,該運用域僅適用於WebApplicationContext環境

singleton 作用域:

singleton 是預設的作用域,也就是說,當定義 Bean 時,如果沒有指定作用域配置項,則 Bean 的作用域被預設為 singleton。

當一個bean的作用域為Singleton,那麼Spring IoC容器中只會存在一個共享的bean例項,並且所有對bean的請求,只要id與該bean定義相匹配,則只會返回bean的同一例項。

也就是說,當將一個bean定義設定為singleton作用域的時候,Spring IoC容器只會建立該bean定義的唯一例項。

Singleton是單例型別,就是在建立起容器時就同時自動建立了一個bean的物件,不管你是否使用,他都存在了,每次獲取到的物件都是同一個物件。注意,Singleton作用域是Spring中的預設作用域。你可以在 bean 的配置檔案中設定作用域的屬性為 singleton,如下所示:

<!-- A bean definition with singleton scope -->
<bean id="..." class="..." scope="singleton">
    <!-- collaborators and configuration for this bean go here -->
</bean>

prototype 作用域

當一個bean的作用域為Prototype,表示一個bean定義對應多個物件例項。Prototype作用域的bean會導致在每次對該bean請求(將其注入到另一個bean中,或者以程式的方式呼叫容器的getBean()方法)時都會建立一個新的bean例項。Prototype是原型型別,它在我們建立容器的時候並沒有例項化,而是當我們獲取bean的時候才會去建立一個物件,而且我們每次獲取到的物件都不是同一個物件。根據經驗,對有狀態的bean應該使用prototype作用域,而對無狀態的bean則應該使用singleton作用域。

為了定義 prototype 作用域,你可以在 bean 的配置檔案中設定作用域的屬性為 prototype,如下所示:

<!-- A bean definition with singleton scope -->
<bean id="..." class="..." scope="prototype">
   <!-- collaborators and configuration for this bean go here -->
</bean>

​ ----相關參考見w3cschool文