JavaWeb——Spring的IoC

JavaWeb——Spring 系列

二、Spring IoC

  • 在上一篇介绍了 Spring 的基本组成,这一篇将记录我对 Spring 的 IoC 的学习。
  • 所谓 IoC,就是控制反转(Inversion of Control),使程序组件或类之间尽可能形成一种松耦合的结构,在传统 Java 编程中,如果要使用一个类,就必须先创建类的对象实例;而在 Spring 编程中,这一步不在由开发者编写,而是交由 IoC 容器进行对象实例化;实现这个过程的操作,称之为依赖注入(Dependency Injection)

1、依赖注入

  • 依赖注入有三种实现方式:接口注入、Setter 注入和构造器注入。
  • 所谓接口注入,是指基于接口将调用与实现分离。
  • Setter 注入,基于 JavaBean 的 Setter 方法为属性赋值,实际开发中广泛使用。
  • 构造器注入就是利用类的构造方法为属性赋值。
  • Spring 支持后两者。

1.1、Setter 注入示例

  • 见上一篇中的 Spring 简单示例

1.2、构造器示例

  • 首先建一个 Java 类,代码如下:
    //IntelliJ IDEA
    //Sprin01
    //Agent
    //2020/1/11
    // Author:御承扬
    //E-mail:[email protected]
    
    package com.myCode.beanSet;
    
    public class Agent {
        private String name;
        private Integer age;
        private String sex;
        private String addr;
        public Agent(String name,Integer age, String sex, String addr){
            this.name=name;
            this.age=age;
            this.sex=sex;
            this.addr=addr;
        }
        public void printInfo(){
            System.out.println("客户姓名:"+name);
            System.out.println("客户年龄:"+age);
            System.out.println("客户性别:"+sex);
            System.out.println("客户地址:"+addr);
        }
    }
    
  • 在 applicationContext.xml 文件中增加以下代码:
    <bean name="agent" class="com.myCode.beanSet.Agent">
        <constructor-arg value="时风"/>
        <constructor-arg value="26"/>
        <constructor-arg value=""/>
        <constructor-arg value="史兰县"/>
    </bean>
    
  • 在 Manager.java 中增加如下代码:
    Agent agent = (Agent)factory.getBean("agent");
    agent.printInfo();
    
  • 输出如下:
    客户姓名:时风
    客户年龄:26
    客户性别:男
    客户地址:史兰县
    

2、Bean 的自动装配

  • Spring 的配置文件 applicationContext.xml 的<bean>标签的 autowire 属性,支持对指定的 JavaBean 的相关属性进行自动装配。

2.1、自动装配的优缺点

  • 通过使用自动装配可以节省许多 JavaBean 属性的标签代码,从而使得代码更为整洁,这个就是自动装配的优点。
  • 自动装配的缺点在于,使用了自动装配方式后,很难通过阅读配置文件了解 JavaBean 需要什么属性。

2.2、自动装配的分类

  • 按照自动装配的实现机制,可以分为:按 bean 名称装配、按 bean 类型装配。

2.2、自动装配示例

  • 这里贴出按 bean 名称装配的示例,因为按 bean 类型装配的只需要将 autowire 的属性值设置为 byType 即可。
  • 示例代码如下:
  • 首先新建一个 PrintAgentInfo 类,代码如下:
    //IntelliJ IDEA
    //Sprin01
    //PrintAgentInfo
    //2020/1/12
    // Author:御承扬
    //E-mail:[email protected]
    
    package com.myCode.beanSet;
    
    public class PrintAgentInfo {
        private Agent agent;
    
        public Agent getAgent() {
            return agent;
        }
    
        public void setAgent(Agent agent) {
            this.agent = agent;
        }
        public void PrintAgent(){
            System.out.println("PrintAgentInfo 打印的 Agent 属性");
            System.out.println("客户姓名:"+agent.getName());
            System.out.println("客户年龄:"+agent.getAge());
            System.out.println("客户性别:"+agent.getSex());
            System.out.println("客户地址:"+agent.getAddr());
        }
    }
    
  • 接着对 Agent 类进行适当修改,增加属性的 set 方法和 get 方法,如下:
    public void setName(String name) {
        this.name = name;
    }
    
    public void setSex(String sex) {
        this.sex = sex;
    }
    
    public void setAge(Integer age) {
        this.age = age;
    }
    
    public void setAddr(String addr) {
        this.addr = addr;
    }
    
    public String getName() {
        return name;
    }
    
    public String getSex() {
        return sex;
    }
    
    public Integer getAge() {
        return age;
    }
    
    public String getAddr() {
        return addr;
    }
    
  • 在 applicationContext.xml 文件中增加如下一句话:
    <bean autowire="byName" id="printAgentInfo" class="com.myCode.beanSet.PrintAgentInfo"/>
    
  • 在 Manager 中对 PrintAgentInfo 进行使用:
    PrintAgentInfo printAgentInfo = (PrintAgentInfo)factory.getBean("printAgentInfo");
    printAgentInfo.PrintAgent();
    
  • 效果如下:
    PrintAgentInfo 打印的 Agent 属性
    客户姓名:时风
    客户年龄:26
    客户性别:男
    客户地址:史兰县
    

3、Spring 中 Bean 的作用域

  • bean 在 Spring 编程中,可以理解为一种由 Spring 容器初始化、装配和管理的对象。
  • 在 Spring 中 bean 由配置文件(XML 文件)的 <bean> 标签来声明,该元素通过属性 scope 来确定 bean 的作用,scope 可选值为:singleton 和 prototype。

3.1、singleton

  • 当 bean 的作用域为 singleton 时,Spring IoC 容器中只会存在一个共享的该 bean 实例,并且所有对该 bean 的引用,若 id 和 name 匹配就返回 bean 的单一实例;此时,bean 的生命周期和 Spring IoC 容器的是一致的;bean 默认作用域为 singleton
  • 示例:
    <bean id="demo" class="Demo"/>
    <bean id="demo" class="Demo" singleton="true"/>
    <bean id="demo" class="Demo" scope="singleton"/>
    

3.2、prototype

  • prototype 作用域的 bean 会在每次请求时创建一个新的 bean 实例返回给请求方,并将该实例的生命周期交给请求方管理,因此需要使用 bean 的后置处理器清除 prototype 作用域的 bean(后置处理器需持有要被清除的 bean 的引用)。
  • 鉴于 prototype 作用域的特性,所有有状态的 bean 应当使用 prototype作用域,无状态的则使用 singleton 作用域。
  • 示例
    <bean id="demo" class="Demo" singleton="false"/>
    <bean id="demo" class="Demo" scope="prototype"/>
    

上一篇
下一篇

发布了146 篇原创文章 · 获赞 15 · 访问量 1万+

猜你喜欢

转载自blog.csdn.net/qq_42896653/article/details/103948220
今日推荐