Spring(一):Spring核心与设计思想(IoC、DI)

news2024/11/17 7:25:46

目录

  • 一、Spring是什么
    • 1.1 容器是什么?
    • 1.2 什么是IoC?
    • 1.3 理解Spring IoC
    • 1.4 DI是什么

一、Spring是什么

我们这里所说的Spring指的是SpringFrameWork,是一个开源框架。Spring支持广泛的应用场景,它可以让Java企业级的应用程序开发起来更简单。
一句话概括就是,Spring是包含了众多工具方法的IoC容器

1.1 容器是什么?

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

在之前我们用过的容器有,List/Map/Set -> 数据存储容器,Tomcat -> Web容器

1.2 什么是IoC?

IoC = Inversion of Control 翻译成中⽂是“控制反转”的意思,也就是说 Spring 是⼀个“控制反转”的容器

在看下面的示例之前我们先想一个问题,当我们在A类中需要B类时,应该怎样得到B类呢?我们正常的想法肯定是,既然我在A类中需要使用B,那么我直接在A类中new B()不就可以了吗。这种做法可以实现,但是有弊端-代码之前耦合度太高。
而控制反转的思想是怎么做的呢?之前在A类中需要使用B类,需要程序员自己通过程序和代码来控制B的生命周期(也就是控制B的创建和销毁),Spring提供的实现方式是,如果在A类中需要使用B,此时不需要在A类中通过new 的方式得到B,也就是不需要再A类中控制B类的生命周期了,可以将这个控制权交给Spring,我们要在A类中使用B,直接从Spring中获取B就可以了。

【传统程序开发】
假如,我们现在构建⼀辆"车"的程序,我们的实现思路是这样的:建⼀辆车(Car Class),然而车需要依赖车身(FrameWork Class),而车身需要依赖底盘(BottomClass),而底盘需要依赖轮胎(Tire Class),最终程序的实现代码如下
在这里插入图片描述
代码实现:

public class NewCarExample {
    public static void main(String[] args) {
        Car car = new Car();
        car.init();
    }

    /**
     * 汽⻋对象
     */
    static class Car {
        public void init() {
            // 依赖⻋身
            Framework framework = new Framework();
            framework.init();
        }
    }

    /**
     * ⻋身类
     */
    static class Framework {
        public void init() {
            // 依赖底盘
            Bottom bottom = new Bottom();
            bottom.init();
        }
    }

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

    /**
     * 轮胎类
     */
    static class Tire {
        private int size = 30;
        
        public void init() {
            System.out.println("轮胎尺⼨:" + size);
        }
    }
}

以上程序中,轮胎的尺寸的固定的,然而随着对的车的需求量越来越大,个性化需求也会越来越多,这时候我们就需要加工多种尺寸的轮胎,那这个时候就要对上面的程序进行修改了,修改后的代码如下所示:

public class NewCarUpdateExample {
    public static void main(String[] args) {
        Car car = new Car(20);
        car.run();
    }

    /**
     * 汽⻋对象
     */
    static class Car {
        private Framework framework;

        public Car(int size) {
            framework = new Framework(size);
        }

        public void run() {
            // 依赖⻋身
            framework.init();
        }
    }

    static class Framework {
        private Bottom bottom;

        public Framework(int size) {
            bottom = new Bottom(size);
        }

        public void init() {
            // 依赖底盘
            bottom.init();
        }
    }

    static class Bottom {
        private Tire tire;

        public Bottom(int size) {
            tire = new Tire(size);
        }

        public void init() {
            // 依赖轮胎
            tire.init();
        }
    }

    static class Tire {
        // 尺⼨
        private int size;

        public Tire(int size) {
            this.size = size;
        }

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

传统开发的问题:当最底层代码改动之后,整个调用链上的所有代码都需要修改

如何解决这个问题呢?

我们可以尝试不在每个类中自己创建下级类,这种方式代码之间的耦合性太高,因此我们只需将原来自己创建的下机类,改为传递的方式(也就是注入的方式),因此我们不需要在当前类中创建下级类了,所以下级类即使发生变化(增加或减少参数),当前类本身也不用修改任何代码,从而完成了程序的解耦。

【控制反转式程序开发】
我们把调⽤汽⻋的程序示例改造⼀下,把创建⼦类的⽅式,改为注⼊传递的⽅式,具体实现代码如下:

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();
    }

    static class Car {
        private Framework framework;

        public Car(Framework framework) {
            this.framework = framework;
        }

        public void run() {
            framework.init();
        }
    }

    static class Framework {
        private Bottom bottom;

        public Framework(Bottom bottom) {
            this.bottom = bottom;
        }

        public void init() {
            bottom.init();
        }
    }

    static class Bottom {
        private Tire tire;

        public Bottom(Tire tire) {
            this.tire = tire;
        }

        public void init() {
            tire.init();
        }
    }

    static class Tire {
        private int size;

        public Tire(int size) {
            this.size = size;
        }

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

代码经过以上调整,无论底层类如何变化,整个调用链是不用做任何改变的,这样就完成了代码之间的解耦,从而实现了更加灵活、通用的程序设计了
在这里插入图片描述
【对比上述两种开发程序的方式】

  • 在传统的代码中,对象创建的顺序为:Car->FrameWork->Bottom->Tire
  • 在控制反转的程序中,对象创建的顺序为:Tire->Bottom->FrameWork->Car

1.3 理解Spring IoC

既然Spring是一个IoC容器,作为容器,它就具备两个最基础的功能,将对象存入到容器从容器中取出对象
Spring最核心的功能就是存储对象

【将对象放到容器中的好处】

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

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

1.4 DI是什么

DI是Dependency Injection的缩写,"依赖注入"的意思,所谓依赖注入,就是指IoC容器在运行期间,动态的将某种依赖关系注入到对象中。所以DI和IoC是从不同的角度去描述的同一件事情。
IoC是一种思想,DI就是这种思想的一个具体实现方式

【IoC和DI的区别】
IoC是一种思想,实现IoC的方式有很多,DI只是其中的一种

【举例区分IoC和DI】

今晚我想去吃顿夜宵,夜宵的种类有很多,例如,火锅、烧烤…"想要吃夜宵"就是一种思想,吃火锅或烧烤就是这种思想的具体实现

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/82944.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

k8s编程operator实战之云编码平台——②controller初步实现

文章目录1、工作空间镜像制作2、controller实现2.1 使用kubebuilder创建工程2.2 代码实现2.2.1 引入grpc2.2.2 实现CloudIdeServiceStatusInformer的实现CloudSpaceService定义方法CreateSpaceAndWaitForRunning方法GetPodSpaceInfo方法DeleteSpace方法GetPodSpaceStatus2.2.3 …

人才盘点的工具与方法有哪些?怎样做好人才盘点?

人才盘点是对组织和人才进行系统管理的一种流程。在此过程中,对组织架构、人员配比、人才绩效、关键岗位的继任计划、关键人才发展、关键岗位的招聘及关键人才的晋升和激励进行深入讨论,并制定详细的组织行动计划,确保组织以更加优化的结构和…

非零基础自学计算机操作系统 第1章 操作系统概述 1.5 操作系统的硬件环境 1.5.1 定时装置 1.5.2 堆与栈 1.5.3 寄存器

非零基础自学计算机操作系统 文章目录非零基础自学计算机操作系统第1章 操作系统概述1.5 操作系统的硬件环境1.5.1 定时装置1.5.2 堆与栈1.5.3 寄存器第1章 操作系统概述 1.5 操作系统的硬件环境 构建一个高效、可靠的操作系统,硬件需要提供哪些支持? 1…

MySQL数据库基本使用(一)-------登录及查看基本信息

1.MySQL登录命令 格式如下: mysql -h 主机名 -P 端口号 -u 用户名 -p密码例如: mysql -h localhost -P 3306 -u root -pabc123 # 这里我设置的root用户的密码是abc123注意: -p与密码之间不能有空格,其他参数名与参数值之间可以…

Spring Boot启动原理源码

Spring Boot启动原理源码 注意:这个springboot启动源码和springboot自动配置原理的源码是十分重要的,面试的时候要是问springboot,一般都会问这两个。 源码: SpringBoot 事假监听器发布顺序: 1.ApplicationStartingEvent 2.ApplicationEnvironmentPrepa…

springboot+mybatis配置多数据源实战

1.背景说明 2.配置多数据源步骤 2.1 项目结构变更 2.2 添加配置类 2.3 修改配置文件数据连接配置信息 1.背景说明一般一个项目中只会连接一个数据库.但是随着需求变更,会要求同一个项目中连接多个数据库,本文就讲一下如何在一个项目中对多…

usaco training刷怪旅 第一层第二题 Greedy Gift Givers

usaco training 关注我持续创作training题解 翻译有点奇葩,我就上原题目了,各位自己翻译吧QwQ A group of NP (2 ≤ NP ≤ 10) uniquely named friends has decided to exchange gifts of money. Each of these friends might or might not give some m…

一种基于PCI总线的反射内存卡设计

一种基于PCI总线的反射内存卡设计 摘要: 对实时传输, 传统的以太网络由于传输协议开销的不确定性, 很难满足实时网络的要求, 实时网络是一种应用于高实时性要求的专用网络通信技术, 一般采用基于高速网络的共享存储器…

Python爬虫实战,requests+openpyxl模块,爬取小说数据并保存txt文档(附源码)

前言 今天给大家介绍的是Python爬取小说数据并保存txt文档,在这里给需要的小伙伴们代码,并且给出一点小心得。 首先是爬取之前应该尽可能伪装成浏览器而不被识别出来是爬虫,基本的是加请求头,但是这样的纯文本数据爬取的人会很多…

web网页设计与开发:基于HTML+CSS+JavaScript简单的个人博客网页制作期末作业

🎉精彩专栏推荐👇🏻👇🏻👇🏻 ✍️ 作者简介: 一个热爱把逻辑思维转变为代码的技术博主 💂 作者主页: 【主页——🚀获取更多优质源码】 🎓 web前端期末大作业…

怎么让文字转换成语音?一步一步让你学会

在日常的生活中,我们经常会需要将文字转换成语音的情况,例如广告词、给文本配音等等,当然我们就简单的方法就是自己手动进行配音,但是如果没有专业的设备和配音环境,是很难配出很好的效果的,这该怎么办呢&a…

飞链云智能机器人-基于ChatGPT的有趣问答

最近ChatGPT火起来了; 可玩性很高,不亚于之前AI绘画的视觉冲击;这次ChatGPT带来的是逻辑冲击;上下文逻辑远超现有市面上其他所有的AI对话机器人; 有人用技巧训练ChatGPT,ChatGPT机器人宣言要毁灭人类&…

备战2023蓝桥国赛-传纸条

题目描述: 解析: 这道题想了我好久,一开始我是想假如只走一条路线,从(1,1)走到(m,n),这种问题该怎么解决呢?针对这种问题我是设了dp[k][i][j]表示走了k步到达(i,j)的好心程度之和的…

[附源码]JAVA毕业设计迎宾酒店管理系统录屏(系统+LW)

[附源码]JAVA毕业设计迎宾酒店管理系统录屏(系统LW) 项目运行 环境项配置: Jdk1.8 Tomcat8.5 Mysql HBuilderX(Webstorm也行) Eclispe(IntelliJ IDEA,Eclispe,MyEclispe,Sts都支持)。 项目…

R语言中使用多重聚合预测算法(MAPA)进行时间序列分析

最近我们被客户要求撰写关于时间序列分析的研究报告,包括一些图形和统计输出。这是一个简短的演示,可以使用该代码进行操作。使用MAPA生成预测。 > mapasimple(admissions)t1 t2 t3 t4 t5 t6 t7 t8 t9 t…

ElasticsearchRestTemplate 和ElasticsearchRepository 的使用

操作ElasticSearch的数据,有两种方式一种是 ElasticsearchRepository 接口,另一种是ElasticsearchTemplate接口 SpringData对ES的封装ElasticsearchRestTemplate类,可直接使用,此类在ElasticsearchRestTemplate基础上进行性一定程…

Kibana:使用 Maps 来显示分布式的团队

在我之前的文章 “Kibana:如何在 Maps 应用中显示图片提示” 里,我展示了如何在 Kibana 中使用图片来展示一个图片的提示。这个在很多情况下是非常有用的,比如在疫情发生期间,我可以通过点击地图上的点来查看发生疫情人员的详细情…

ADI Blackfin DSP处理器-BF533的开发详解40:图像处理专题-GrayStretch 图像的灰度拉伸(含源码)

硬件准备 ADSP-EDU-BF533:BF533开发板 AD-HP530ICE:ADI DSP仿真器 软件准备 Visual DSP软件 硬件链接 功能介绍 代码实现了图像的灰度拉伸,代码运行时,会通过文件系统打开工程文件根目下" …/ImageView"路径中的 t…

回归预测 | MATLAB实现WOA-GRU鲸鱼算法优化门控循环单元多输入单输出回归预测

回归预测 | MATLAB实现WOA-GRU鲸鱼算法优化门控循环单元多输入单输出回归预测 目录回归预测 | MATLAB实现WOA-GRU鲸鱼算法优化门控循环单元多输入单输出回归预测写在前面效果一览基本描述模型描述程序设计参考资料写在前面 程序获取 | 机器学习/深度学习程序获取方式&#xff0…

Django学习第一天记录

1.安装Django(Windows环境) 首先需要确定系统中存在python环境,当前,本机的python环境为python 3.6.6,可以使用命令python --version进行查看。 在python环境成功搭建的基础上,我们使用命令pip install django即可进行django环境…