2、IoC控制反转(四声)

学习资源:动力节点的2020最新Spring框架教程【IDEA版】-Spring框架从入门到精通


1、什么是 IoC控制反转

控制反转(IoC, Inversion of Control),是一个概念,是一种思想。指将传统上由程序代码直接操控的对象调用权交给容器,通过容器来实现对象的装配和管理。控制反转就是对对象控制权的转移,从程序代码本身反转到了外部容器。 通过容器实现对象的创建,属性赋值,依赖的管理。

当前比较流行的实现 IoC 的方式是依赖注入

依赖: classA 类中含有 classB 的实例,在 classA 中调用 classB 的方法完成功能,即 class A 对 class B 有依赖。

依赖注入:DI(Dependency Injection),程序代码不做定位查询,这些工作由容器自行完成。

依赖注入 DI 是指程序运行过程中,若需要调用另一个对象协助时,无须在代码中创建被调用者,而是依赖于外部容器,由外部容器创建后传递给程序。Spring 的依赖注入对调用者与被调用者几乎没有任何要求,完全支持对象之间依赖关系的管理。

Spring 框架使用依赖注入(DI)实现 IoC。

Spring 容器是一个超级大工厂,负责创建、管理所有的 Java 对象,这些 Java 对象被称为 Bean。 Spring 容器管理着容器中 Bean 之间的依赖关系, Spring 使用 DI 的方式来管理 Bean 之间的依赖关系,进而实现对象之间的解耦和。


2、DI 入门实例

2.1、创建 Maven 项目


2.2、引入 Maven 依赖

<dependency>
    <groupId>org.springframework</groupId>
    <artifactId>spring-context</artifactId>
    <version>5.2.5.RELEASE</version>
</dependency>

<build>
<plugins>
    <plugin>
        <artifactId>maven-compiler-plugin</artifactId>
        <version>3.1</version>
        <configuration>
            <source>1.8</source>
            <target>1.8</target>
        </configuration>
    </plugin>
</plugins>
</build>

2.3、定义接口与实体类

public interface SomeService {
    void doSome();
}
// 无属性的实体类
public class SomeServiceImpl implements SomeService {
    
    public SomeServiceImpl() {
        super();
        System.out.println("SomeServiceImpl无参数构造方法");
    }
    @Override
    public void doSome() {
        System.out.println("====业务方法doSome()===");
    }
}

2.4、创建 Spring 配置文件

在 src/main/resources/ 目录下创建一个 xml 文件,applicationContext.xml

image-20200831160308890

文件初始内容:

  • <\beans> 是 Spring 配置文件的根标签
  • spring-beans.xsd 是约束文件
<?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">

</beans>

2.5、注册 bean对象

<\bean> 标签用于在 Spring 容器中声明注册一个实体类的对象。

标签属性:

  • id:该属性是 Bean 实例的唯一标识,自定义名称,程序通过 id 属性访问 Bean, Bean 与 Bean 间的依赖关系也是通过 id 属性关联的。
  • class:指定该 Bean 所属的类,使用类的全限定名称。
    注意: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"
       xsi:schemaLocation="http://www.springframework.org/schema/beans
                           http://www.springframework.org/schema/beans/spring-beans.xsd">

    <bean id="someService" class="com.bjpoewernode.service.impl.SomeServiceImpl" />
    
    <!-- 其他Bean -->
    <bean id="xxx" class="xxx.xxx.xxx" />
    ......
</beans>

Spring 完成 SomeService someService = new SomeServiceImpl(); 的创建,并创建好的对象放入到一个框架内部的 map 中,springMap.put(beanId, 实例对象); ,例如:springMap.put("someService", newSomeServiceImpl());


2.6、测试

2.6.1、获取 Spring 容器中的对象

  1. 指定 Spring 配置文件的位置和名称,applicationContext.xml 通常都放置在 resources 目录下
  2. 创建 Spring 容器的对象,ApplicationContext对象,
    (qaq,怎么还是需要 new 啊😅)
image-20200831170022112
  1. 根据 id 从容器中"拿"对象 getBean ,类型强转,就可以使用该对象了

image-20200831171859928

@Test
public void test01{
    
    String resource="applicationContext.xml";
    ApplicationContext ac = new ClassPathXmlApplicationContext(resource);
    SomeService ss = (SomeService) ac.getBean("someService");
    ss.doSome();
}

2.6.2、获取容器中对象的数量 & 名称(bean id)

@Test
public void test02{
    
    String resource="applicationContext.xml";
    ApplicationContext ac = new ClassPathXmlApplicationContext(resource);
    int count = ac.getBeanDefinitionCount();
    sout("容器中注册的对象数量:"+nums);
    
    String[] names = ac.getBeanDefinitionNames();
    for(String name : names){
        sout(name);
    }
}

2.7、容器创建非自定义类的对象

测试的 Java 类: java.util.Date

在 Spring 配置文件声明注册 java.util.Date

<bean id="utilDate" class"java.util.Date" />

测试:

@Test
public void test03{
    
    String resource="applicationContext.xml";
    ApplicationContext ac = new ClassPathXmlApplicationContext(resource);
    Date myDate = ac.getBean("utilDate");
}

3、容器的接口和实现类

applicationContext 容器

ApplicationContext 用于加载 Spring 的配置文件,在程序中充当“容器”的角色,其实现类有两个:

image-20200831184129461

开发中一般使用 ClassPathXmlApplicationContext 的实例对象,它表示从类路径加载 Spring 的配置文件;而 FileSystemXmlApplicationContext 表示从磁盘中加载。


ApplicationContext 容器中对象的装配时机

前提是,bean 的属性是 singleton。

Spring 默认创建对象的时间:在创建 ApplicationContext 容器时,就会创建配置文件中的所有的对象,一次性全部装配好,默认调用类的无参构造器进行对象的创建。以后代码中若要使用到这些对象,只需从内存中直接获取即可,执行效率较高。

image-20200831184057078

posted @ 2020-09-06 17:08  卡文迪雨  阅读(133)  评论(0编辑  收藏  举报