2021-09-14

1, IOC概念和原理

1)什么是IOC?

  • 控制反转,把对象创建和对象之间的调用过程,交给Spring进行管理。
  • 使用IOC目的,为了耦合度降低。
  • 做入门案例就是IOC实现。

2)IOC底层原理

  • xml解析,工厂模式,反射

3)IOC(接口)

  • IOC思想基于IOC容器完成,IOC容器底层就是对象工厂。
  • Spring提供IOC容器实现两种方式:(两个接口)
    • BeanFactory: IOC容器基本实现,是Spring内部的使用接口,不提供开发人员进行使用。
      注:加载配置文件的时候不会创建对象,而在获取对象的时候才去创建对象
    • ApplicationContext:BeanFactory接口的子接口,提供更多强大的功能,一般由开发人员进行使用。
      注:加载配置文件的时候就可以创建对象

2,IOC容器-Bean管理XML方式— 注入(Injection)

2.1, 什么是注入

1,通过Spring工厂及配置文件,为所创建对象的成员变量赋值。

2.2, 为什么需要注入?

1,通过编码的方式,为成员变量进行赋值,存在耦合

public static void test6(){
         ApplicationContext ctx = new ClassPathXmlApplicationContext("/applicationContext.xml");
         User user = ctx.getBean("User", User.class);
         //以下代码存在耦合
         user.setAge(4);
         user.setName("夏木"); 
     }

2.3, 如何进行注入【开发步骤】

  • 类为成员变量提供set, get方法
  • 配置Spring的配置文件
<bean id="User" name="U,u" class="User">
        <property name="age">
              <value>12</value>
        </property>
        <property name="name">
            <value>王八犊子</value>
        </property>
</bean>

SpringFactory

 public static void test7(){
         ApplicationContext ctx = new ClassPathXmlApplicationContext("/applicationContext.xml");
         User user = ctx.getBean("User", User.class);

         System.out.println("user = " + user);
     }

2.4, 注入好处

1, 解耦合

3,创建对象和set的方式注入属性

3.1,针对不同类型的成员变量,在标签,需要嵌套其他标签

1) 八种基本类型:

<property name="property"></property>

2) 数组或List集合

<property name="property">
   <list>
        <value></value>或其他
   </list>
</property>

3) Set集合

<property name="proterty">            
     <set> 
      <value></value>或者<bean id="id" Class="classPath"/> 或者其他
     </set>
 </property>

4) Map集合

<property name="proterty">
   <map>
     <entry>
        <key><value> key </value></key>
             <value> value </value>
     </entry>
   </map>
</property>

5) properties类型

<property name="proterty">
     <props>
         <prop key="key1">value1</prop>
         <prop key="key2">value2</prop>
    </props>
</property>

6) 复杂JDK类型

需要程序员自定义类型转换器。。。`

7)用户自定义类型

<bean id="userDao" class="XXX.userDaoImpl"/>
                                   
<bean id="userService" class="XXX.userServiceImpl">
      <property name="userDao"><ref bean="userDao"/></property>
</bean>
 简化:
<bean id="userDao" class="XXX.userDaoImpl"/>
                                     `
<bean id="userService" class="XXX.userServiceImpl">
      <property name="userDao" ref="userDao"/>
</bean>

3.2,基于P命名空间简化

1)JDK类型注入

<bean id="XXX" class="XXX" p:name="张三"/>

2)自定义类型注入

<bean id="userDao" class="userDaoImpl"/>
<bean id="userService" class="userServiceImpl"  p:userDao-ref="userDao"/>

注意:这里只能简化八种基本类型和用户自定义类型

4,有参构造注入属性

<bean id="user" class="com.company.Spring.User">
        <constructor-arg name="name" value="小光"></constructor-arg>
        <constructor-arg name="age" value="12"></constructor-arg>
</bean>

另一种写法:

<bean id="user" class="com.company.Spring.User">
        <constructor-arg index="0" value="小光"></constructor-arg>
        <constructor-arg index="1" value="12"></constructor-arg>
</bean>

5,注入空值和特殊符号

  • 注入空值
<property name="property">
       <null/>
</property>
  • 特殊符号
    • 把特殊符号进行转义, 例如:&lt; &gt;
    • 把带特殊符号内容写到CDTAT
<property name="property"> 
     <value><![CDATA[含特殊符号的内容]]></value>
</property>

6,注入外部bean

(1)创建两个Service类和dao类
(2)在service调用dao里面的方法
(3)在spring配置文件中进行配置

2021-09-14

bean1.xml文件中

<bean id="userService" class="com.company.UserService">
    <property name="userDao" ref="userDaoImpl">
    </property>
</bean>
<bean id="userDaoImpl" class="com.company.UserDaoImpl"></bean>

6,注入内部bean和级联赋值

  • 注入内部bean
    (以员工和部门为例子)
    (1)一对多关系,部门和员工
    (2)在实体类之间表示一对多关系

部门类

package com.company.test;

public class Dept {
    private String dname;
    public void setDname(String dname){
        this.dname = dname;
    }
    public String getDname() {
        return dname;
    }
}

员工类

package com.company.test;

public class Emp {
    private String ename;
    private String gender;
    private Dept dept;

    public void setDept(Dept dept) {
        this.dept = dept;
    }

    public void setGender(String gender) {
        this.gender = gender;
    }

    public void setEname(String ename) {
        this.ename = ename;
    }

      public Dept getDept() {
        return dept;
    }

    public String getEname() {
        return ename;
    }

    public String getGender() {
        return gender;
    }
}

bean.xml文件

<bean id="emp" class="com.company.test.Emp">
        <property name="ename" value="张三"></property>
        <property name="gender" value="男"></property>
        <property name="dept">
            <bean id="dept" class="com.company.test.Dept">
                <property name="dname" value="保安部"></property>
            </bean>
        </property>
    </bean>
  • 级联赋值

(只需更改bean.xml文件)

<bean id="emp" class="com.company.test.Emp">
        <property name="ename" value="张三"></property>
        <property name="gender" value="男"></property>
        <property name="dept" ref="dept"/>
 </bean>
 <bean id="dept" class="com.company.test.Dept">
          <property name="dname" value="保安部"></property>
 </bean>

7,工厂bean

  • Spring有两种类型bean, 一种普通bean,另为一种工厂bean(FactoryBean)
  • 普通bean:在配置文件中定义bean类型就是返回类型
  • 工厂bean: 在配置文件中定义bean类型可以与返回值类型不一样
    • 第一步创建类,让这个类作为工厂bean,实现接口FactoryBean
    • 第二步实现接口里面的方法,在实现的方法中定义返回的bean类型

8, bean的作用域

  • 在Spring里面,设置创建bean实例是默认单实例对象
  • 设置多实例对象的方法:
    • 在Spring配置文件bean标签里面有属性(scope) 用于设置单实例还是多实例
    • scope属性值 :第一个值为singleton, 表示单实例对象,第二个值为prototype,表示多实例对象
  • singleton和prototype区别
    • singleton 单实例,prototype多实例
    • 设置scope值是singleton时候,加载spring配置文件时候就会创建单实例对象
    • 设置scope值是prototype时候,不是在加载spring配置文件时候创建对象,在调用getBean方法时候创建多实例对象

9,bean的生命周期

1,生命周期: 从对象创建到对象销毁的过程。
2,bean的生命周期
(1)通过构造器创建bean实例(无参构造)
(2)为bean的属性设置值和对其他bean引用(调用set方法)
(3)把bean实例传递bean后置处理器的方法
(4)调用bean的初始化的方法(需要配置方法)
(5)把bean实例传递bean后置处理器的方法
(6)bean可以使用了(对象获取到了)
(7)当容器关闭时候,调用bean的销毁方法(需要配置方法)

1) 配置初始化方法

Student类中添加

public void initmethod(){
        System.out.println("初始化");
}

XML文件中设置init-method属性

<bean id="student" class="com.company.test.Student" init-method="initmethod"/>

2)配置销毁方法

Student类中添加

public void destorymethod(){
        System.out.println("销毁对象");
}

XML文件中设置init-method属性

<bean id="student" class="com.company.test.Student" destroy-method="destroyMethod"/>

测试

    @Test
    public void test(){
          ClassPathXmlApplicationContext ctx = new ClassPathXmlApplicationContext("bean1.xml");
          Object obj = ctx.getBean("student", Student.class);
          System.out.println(obj.toString());

          ctx.close();
          System.out.println("对象已销毁");
   }

3)实现后置处理器
2021-09-14
XML
2021-09-14

10,XML实现自动装配

(该方法不常用)

配置XML文件

<!--实现自动装配
       bean标签属性autowire, 配置自动装配
       autowire属性常用两个值:
            byName根据属性名字注入,注入值bean的id值和类属性名称一样
            byType根据属性类型注入
    -->
 <bean id="emp" class="com.company.autoWrie.Emp" autowire="byName">
          <!--<property name="dept" ref="dept"></property>-->
 </bean>

Java文件

package com.company.autoWrie;

public class Emp {
    private Dept dept;

    public Dept getDept() {
        return dept;
    }

    public void setDept(Dept dept) {
        this.dept = dept;
    }

    @Override
    public String toString() {
        return "Emp{" +
                "dept=" + dept +
                '}';
    }

    public void test(){
        System.out.println(dept);
    }
}

11,外部文件属性

  • 直接配置数据库信息
    • 配置德鲁伊连接池
    • 引入德鲁伊连接池依赖或jar包
      如图:2021-09-14
      配置XML文件
 <bean id="dataSource" class="com.alibaba.druid.pool.DruidDataSource">
          <property name="driverClassName" value="com.mysql.jdbc.Driver"></property>
          <property name="url" value="jdbc:mysql://localhost:3306/StudentSystem"></property>
          <property name="username" value="root"></property>
          <property name="password" value="123456"></property>
     </bean>
  • 引入外部属性文件配置数据库连接池
    • 配置properties文件
prop.driverClass=com.mysql.jdbc.Driver
prop.url=jdbc:mysql://localhost:3306/StudentSystem
prop.userName=root
prop.password=123456
  • 把外部properties属性文件引入到spring配置文件中
<!--          引入外部属性文件-->
     <context:property-placeholder location="classpath:jdbc.properties"/>
<!--配置连接池-->
          <bean id="dataSource" class="com.alibaba.druid.pool.DruidDataSource">
               <property name="driverClassName" value="${prop.driverClass}"></property>
               <property name="url" value="${prop.url}"></property>
               <property name="username" value="${prop.userName}"></property>
               <property name="password" value="${prop.password}"></property>

          </bean>
上一篇:深入Spring框架


下一篇:IOC学习01