1. Spring 核心与设计思想

目录

[1. Spring 是什么?](#1. Spring 是什么?)

[1.1 什么是容器?](#1.1 什么是容器?)

[1.2 什么是 Ioc ?](#1.2 什么是 Ioc ?)

[1.2.1 传统程序开发](#1.2.1 传统程序开发)

[1.2.2 解决传统开发的缺陷](#1.2.2 解决传统开发的缺陷)

[1.2.3 控制反转式程序开发](#1.2.3 控制反转式程序开发)

[1.2.4 IoC 的实现思想(重点)](#1.2.4 IoC 的实现思想(重点))

[1.3 理解 Spring Ioc](#1.3 理解 Spring Ioc)

[1.4 DI 概念说明](#1.4 DI 概念说明)


1. Spring 是什么?

Spring 指的是 Spring Framework (spring 框架),它是一个开源框架,有着活跃而庞大的社区,这就是它之所以能长久不衰的原因。

Spring 是包含了众多工具方法的 IoC 容器。

1.1 什么是容器?

容器是用来容纳某种物品的装置。

  • List/Map -> 数据存储容器
  • Tomcat -> Web容器

1.2 什么是 Ioc ?

IoC = Inversion of Control 即 控制反转,也就是说 Spring 是一个"控制反转"的容器。

1.2.1 传统程序开发

是通过一层一层的依赖实现的。比如我们要构建一辆车,需要依赖车身,车身进而需要依赖底盘,底盘又需要依赖轮胎。因此一般的实现代码如下:

在 NewCarUpateExample 类中:

java 复制代码
public class NewCarUpateExample {
    public static void main(String[] args) {
        Car car = new Car();
        car.init();
    }
}

首先,我们先创建一个汽车对象:

java 复制代码
/**
 * 汽车对象
 */
public class Car {
    public void init(){
        // 依赖车身
        Framework framework = new Framework();
        framework.init();
    }
}

由于汽车对象需要依赖车身,因此我们创建一个车身类:

java 复制代码
/**
 * 车身类
 */
public class Framework {
    public void init(){
        // 依赖底盘
        Bottom bottom = new Bottom();
        bottom.init();
    }
}

又因为车身依赖于底盘,因此创建底盘类:

java 复制代码
/**
 * 底盘类
 */
public class Bottom {
    public void init(){
        // 依赖轮胎
        Tire tire = new Tire();
        tire.init();
    }
}

最后,因为底盘依赖于轮胎,因此创建轮胎类:

java 复制代码
/**
 * 轮胎类
 */
public class Tire {
    // 轮胎尺寸
    private int size = 30;

    public void init(){
        System.out.println("轮胎尺寸" + size);
    }
}

在以上程序中,轮胎的尺寸是固定的,但是实际中根据各种需求,轮胎的尺寸也会发生变化,因此修改代码如下:

在 NewCarUpateExample 类中:

java 复制代码
public class NewCarUpateExample {
    public static void main(String[] args) {
        Car car = new Car(20);
        car.run();
    }
}
java 复制代码
/**
 * 汽车对象
 */
public class Car {
    private Framework framework;

    public Car(int size){
        framework = new Framework(size);
    }
    public void run(){
        // 依赖车身
        framework.init();
    }
}
java 复制代码
/**
 * 车身类
 */
public class Framework {
    private Bottom bottom;

    public Framework(int size){
        bottom = new Bottom(size);
    }
    public void init(){
        // 依赖底盘
        bottom.init();
    }
}
java 复制代码
/**
 * 底盘类
 */
public class Bottom {
    private Tire tire;
    public Bottom(int size){
        tire = new Tire(size);
    }
    public void init(){
        // 依赖轮胎
        tire.init();
    }
}
java 复制代码
/**
 * 轮胎类
 */
public class Tire {
    // 轮胎尺寸
    private int size;
    public Tire(int size){
        this.size = size;
    }
    public void init(){
        System.out.println("轮胎尺寸" + size);
    }
}

从以上代码可以看出:当最底层的代码修改后,其他层的代码均需要进行修改。

1.2.2 解决传统开发的缺陷

如何解决代码之间的耦合性过高的问题呢?

我们只需要将原来自己创建的下级类,改为传递的方式(也就是注入 ),因为我们不需要在当前类中创建下级类,所以下级类发生变化时,当前类本身就无需再进行修改,这样就完成了程序的解耦

1.2.3 控制反转式程序开发

接下来,在上述程序的基础上,我们将创建子类的方式改为注入传递的方式。

java 复制代码
public class IocCarExample {
    public static void main(String[] args) {
        Tire tire = new Tire(20);
        Bottom bottom = new Bottom(tire);
        Framework framework = new Framework(bottom);
        Car car = new Car(framework);
        car.run();
    }
}
java 复制代码
/**
 * 汽车对象
 */
public class Car {
    private Framework framework;

    public Car(Framework framework){
        this.framework = framework;
    }
    public void run(){
        // 依赖车身
        framework.init();
    }
}
java 复制代码
/**
 * 车身类
 */
public class Framework {
    private Bottom bottom;

    public Framework(Bottom bottom){
        this.bottom = bottom;
    }
    public void init(){
        // 依赖底盘
        bottom.init();
    }
}
java 复制代码
/**
 * 底盘类
 */
public class Bottom {
    private Tire tire;
    public Bottom(Tire tire){
        this.tire = tire;
    }
    public void init(){
        // 依赖轮胎
        tire.init();
    }
}
java 复制代码
/**
 * 轮胎类
 */
public class Tire {
    // 轮胎尺寸
    private int size;
    public Tire(int size){
        this.size = size;
    }
    public void init(){
        System.out.println("轮胎尺寸" + size);
    }
}

代码经过以上调整之后,无论底层如何变化,整个调用链是不用做任何改变的,这样就完成了代码之间的解耦

1.2.4 IoC 的实现思想(重点)

在传统代码中对象创建的规律是:Car -> Framework -> Bottom -> TIre

改进之后解耦的代码的对象创建顺序是:TIre -> Bottom -> Framework -> Car

改进之后的控制权发生的反转,不再是上级对象创建并控制下级对象了,而是把下级对象注入当前对象中,下级的控制权不再由上级类控制了,这样即使下级类发⽣任何改变,当前类都是不受影响的,这就是典型的控制反转,也就是 IoC 的实现思想

(对于依赖对象的管理的控制权反转,通过 Spring 来管理对象的生命周期。不是所有的对象都交给 Spring 管理,需要程序来告诉 Spring 管理哪些对象)。

1.3 理解 Spring Ioc

既然 Spring 是⼀个 IoC(控制反转)容器,重点还在"容器"⼆字上,那么它就具备两个最基础的功

能:

  • 将对象存入到容器;
  • 从容器中取出对象。

也就是说学 Spring 最核心的功能,就是学如何将对象存入到 Spring 中,再从 Spring 中获取对象的过程

将对象存放到容器中的好处:将对象存储在 IoC 容器相当于将以后可能⽤的所有工具制作好都放到仓库中,需要的时候直接取就行了,用完再把它放回到仓库。而 new 对象的方式相当于,每次需要工具了,才现做,用完就扔掉了也不会保存,下次再⽤的时候还得重新做,这就是 IoC 容器和普通程序开发的区别。

Spring 是⼀个 IoC 容器,即对象的创建和销毁的权利都交给 Spring 来管理了,它本身又具备了存储对象和获取对象的能力。

1.4 DI 概念说明

DI 是 Dependency Injection 的缩写,即 依赖注入

**所谓依赖注⼊,就是由 IoC 容器在运行期间,动态地将某种依赖关系注⼊到对象之中(通过构造函数把依赖对象注入进来)。**所以,依赖注⼊(DI)和控制反转(IoC)是从不同的⻆度的描述的同⼀件事情,就是指通过引入 IoC 容器,利用依赖关系注入的⽅式,实现对象之间的解耦。

IoC 是"目标"也是⼀种思想,而目标和思想只是⼀种指导原则,最终还是要有可行的落地⽅案,而 DI就属于具体的实现(即 IoC 是思想,DI 是具体实现)。

相关推荐
TangKenny7 分钟前
计算网络信号
java·算法·华为
肘击鸣的百k路8 分钟前
Java 代理模式详解
java·开发语言·代理模式
城南vision14 分钟前
Docker学习—Docker核心概念总结
java·学习·docker
wyh要好好学习21 分钟前
SpringMVC快速上手
java·spring
尢词23 分钟前
SpringMVC
java·spring·java-ee·tomcat·maven
Mr. zhihao30 分钟前
享元模式在 JDK 中的应用解析
java·享元模式
茶馆大橘33 分钟前
微服务系列五:避免雪崩问题的限流、隔离、熔断措施
java·jmeter·spring cloud·微服务·云原生·架构·sentinel
wrx繁星点点33 分钟前
享元模式:高效管理共享对象的设计模式
java·开发语言·spring·设计模式·maven·intellij-idea·享元模式
真的想不出名儿37 分钟前
Java基础——反射
java·开发语言
鱼跃鹰飞39 分钟前
大厂面试真题-简单说说线程池接到新任务之后的操作流程
java·jvm·面试