Spring-IOC学习笔记-03DI依赖注入

Posted Moon&&Dragon

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了Spring-IOC学习笔记-03DI依赖注入相关的知识,希望对你有一定的参考价值。

DI依赖注入

在一个类里面需要依赖另一个类,之前使用时是在类中去new另外的类。而使用了spring后,spring使用依赖注入(DI)的方式,将bean或者参数注入到另一个bean中。

  • 注入基本数据类型和字符串时使用 value
  • 注入引用类型,引用其他bean使用 ref

5.1 基于构造器注入

通过构造器注入

和前面的创建一样,通过构造器创建时注入,注入的方法有三种。

  • 通过参数name赋值(常用)

    <bean id="lili" class="com.moon.entity.Woman">
      <constructor-arg name="name" value="莉莉"/>
      <constructor-arg name="age" value="18"/>
      <constructor-arg name="outLook" value="面容较好的"/>
    </bean> 
    
  • 通过下标赋值(下标从0开始,下标对应的属性由构造器决定)

    <bean id="lili" class="com.moon.entity.Woman">
      <constructor-arg index="0" value="莉莉"/>
      <constructor-arg index="1" value="18"/>
      <constructor-arg index="2" value="面容较好的"/>
    </bean>
    
  • 通过类型赋值

    <bean id="lili" class="com.moon.entity.Woman">
      <constructor-arg type="java.lang.String" value="莉莉"/>
      <constructor-arg type="int" value="18"/>
      <constructor-arg type="java.lang.String" value="面容较好的"/>
    </bean>
    

5.2 基于Setter方法注入

通过set方法注入,通过该方法,需要确保属性全部有对应的set方法

涉及到的标签是<property>

原理:ioc容器会先去调用bean的无参构造器或者工厂模式去实例一个bean,然后再调用这个bean的set方法,将属性注入。

<bean id="lili" class="com.moon.entity.Woman">
<!--调用set方法注入属性-->
<property name="name" value="莉莉"/>
<property name="age" value="18"/>
<property name="outLook" value="面容较好的"/>
</bean>
  • 注入基本数据类型加String 使用value
  • 注入引用数据类型使用ref来引用

5.2.1 循环依赖

如果出现循环依赖的问题,俩个bean相互依赖,那么就一定需要使用set的方式注入,如果使用构造器方式注入的话,就会出现异常。

原理:在sring中,会先全部实例对应的bean,全部实例号以后,才会对对应的bean进行注入。如果使用构造器注入的话,在实例的时候就需要寻找其他的bean,而此时其他的bean可能还没有实例。

<!-- bean A依赖于B的实例 -->
<bean id="dependencyA" class="com.moon.entity.DependencyA">
  <property name="dependencyB" ref="dependencyB"/>
</bean>

<!-- bean B依赖于A的实例 -->
<bean id="dependencyB" class="com.moon.entity.DependencyB">
  <property name="dependencyA" ref="dependencyA"/>
</bean>

5.2.2 内部注入

可以在一个bean的property中,将property标签不自闭合,然后在property标签中可以声明一个bean

注意:

  • 内部注入的bean,不会受ioc容器接管,在ioc容器中是取不到这个类的,类似于java的内部类。
  • 内部bean仅作用在这个bean的property中,不归容器所有。

SpringIOC容器在处理inner bean时,只负责创建,不负责管理。

<bean id="peter" class="com.moon.entity.Man">
  <property name="name" value="皮特李"/>
  <property name="fund" value="负载累累"/>
  <property name="woman">
    <bean class="com.moon.entity.Woman">
      <property name="name" value="皮特李的秘书"/>
      <property name="outLook" value="聪明能干的"/>
      <property name="age" value="18"/>
    </bean>
  </property>
</bean>

5.2.3 数组的注入

数组的注入,可以将property标签不去自闭合,在标签中使用array标签进行该数组的值的赋值

<bean id="fierceMan" class="com.moon.entity.FierceMan">
  <property name="clothes">
    <array>
      <value>背心</value>
      <value>人字拖</value>
      <value>短裤</value>
    </array>
  </property>
</bean>

5.2.4 List注入

List的注入和array一样,需要在property标签中引用list标签

默认的实现是ArrayList

<bean id="fierceMan" class="com.moon.entity.FierceMan">
  <!--猛男喜欢的电脑颜色-->
  <property name="computerColor">
    <list value-type="java.lang.String">
      <value>粉红色</value>
      <value>玫瑰金</value>
    </list>
  </property>
  <!--猛男喜欢的电脑-->
  <property name="computers">
    <list value-type="com.moon.entity.Computer">
      <bean class="com.moon.entity.Computer" p:boxColor="粉红色"/>
    </list>
  </property>
</bean>

5.2.5 Set注入

和List注入的方式基本一致,需要在property标签中引用set标签

默认的实现类是LinkedHashSet

<bean id="fierceMan" class="com.moon.entity.FierceMan">
  <!--猛男喜欢的雌性-->
  <property name="femaleSet">
    <set value-type="com.moon.entity.Female">
      <!--第一种雌性-->
      <ref bean="female"/>
      <!--第二种雌性-->
      <bean class="com.moon.entity.Female">
        <property name="age" value="18"/>
        <property name="outLook" value="身材好的"/>
      </bean>
    </set>
  </property>
</bean>
<bean id="female" class="com.moon.entity.Female">
  <property name="age" value="51~99"/>
  <property name="outLook" value="长得匹配"/>
</bean>

5.2.6 Map注入

map的注入和之前一样,在property标签先使用map标签,不同的是map标签下注入的是entry,key的声明是在entry标签的属性上。

<bean id="fierceMan" class="com.moon.entity.FierceMan">
  <!--猛男喜欢的卡通-->
  <property name="cartoonMap">
    <map key-type="java.lang.String" value-type="com.moon.entity.Cartoon">
      <!--引用已有bean-->
      <entry key="1" value-ref="baby"/>
      <!--创建内部bean-->
      <entry key="2">
        <bean class="com.moon.entity.Cartoon">
          <property name="cartoonName" value="花园宝宝"/>
        </bean>
      </entry>
    </map>
  </property>
</bean>

<bean id="baby" class="com.moon.entity.Cartoon">
  <property name="cartoonName" value="天线宝宝"/>
</bean>

5.2.7 Properties注入

在spring配置文件也可以注入prop信息,注入的方式和集合的注入基本类似

<bean id="fierceMan" class="com.moon.entity.FierceMan">
  <!--猛男珍藏数据库-->
  <property name="properties">
    <props value-type="java.lang.String">
      <prop key="driverClassName">com.mysql.cj.jdbc.Driver</prop>
      <prop key="url">jdbc:mysql://localhost:3306/test</prop>
      <prop key="username">root</prop>
      <prop key="password">root</prop>
    </props>
  </property>
</bean>

以上是关于Spring-IOC学习笔记-03DI依赖注入的主要内容,如果未能解决你的问题,请参考以下文章

Spring学习笔记4:依赖注入 DI

spring in action学习笔记一:DI(Dependency Injection)依赖注入之CI(Constructor Injection)构造器注入

Laravel 学习笔记:深入理解控制反转(IoC)和依赖注入(DI)

Spring学习系列笔记之Spring心得

Web框架—Spring Framework学习笔记(IoC DI Bean)

Spring-IOC学习笔记-01初识