【面试】Java最新面试题资深开发-Spring篇(1)

问题八:Spring原理

  1. 解释一下什么是Spring框架以及它的核心思想是什么?
  2. Spring中的IoC(控制反转)是什么,它如何实现?
  3. 什么是DI(依赖注入)?Spring是如何支持依赖注入的?

解释一下什么是Spring框架以及它的核心思想是什么?

当然,让我们通过一个简单的例子来说明Spring框架的核心思想,特别是控制反转(IoC)和依赖注入(DI)。

1. 创建一个简单的Java类:

public class MessageService {private String message;public MessageService() {this.message = "Hello, Spring!";}public String getMessage() {return message;}
}

这是一个简单的消息服务类,其中有一个私有的message属性和一个公共的getMessage方法。

2. 使用Spring进行依赖注入:

import org.springframework.context.ApplicationContext;
import org.springframework.context.annotation.AnnotationConfigApplicationContext;public class MainApp {public static void main(String[] args) {// 创建Spring的IoC容器,通过注解配置ApplicationContext context = new AnnotationConfigApplicationContext(AppConfig.class);// 从容器中获取MessageService的实例MessageService messageService = context.getBean(MessageService.class);// 调用getMessage方法System.out.println(messageService.getMessage());}
}

3. 创建Spring配置类:

import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;@Configuration
public class AppConfig {// 声明一个Bean,Spring会将其注册到IoC容器中@Beanpublic MessageService messageService() {return new MessageService();}
}

在这个配置类中,我们使用了@Configuration注解,表示这是一个Spring配置类。其中,@Bean注解用于声明一个Bean,Spring会自动将messageService方法返回的实例注册到IoC容器中。

通过这个简单的例子,你可以看到:

  • MessageService类不再负责自己的实例化,而是由Spring IoC容器来管理。
  • MainApp类通过Spring容器获取MessageService的实例,而不是直接实例化它。

这就是Spring框架的控制反转和依赖注入的体现。Spring负责管理对象的生命周期和依赖关系,开发者只需关注业务逻辑的实现。这种模式使得应用更加松散耦合、可测试和可维护。

Spring中的IoC(控制反转)是什么,它如何实现?

IoC(控制反转)是什么:

控制反转(IoC)是一种设计思想,它将对象的创建和依赖关系的管理交给了容器,而不是由程序员来直接管理。在传统的开发中,程序员负责创建对象并维护它们之间的关系,而在IoC中,这一切都交给了IoC容器。容器负责创建对象、管理对象的生命周期,并注入对象之间的依赖关系。

在Spring中,IoC是通过使用IoC容器来实现的,容器负责管理应用中的组件(例如Java对象)以及这些组件之间的依赖关系。IoC容器负责将对象的创建、初始化、销毁等工作进行统一管理。

IoC容器的实现:

Spring框架实现了IoC容器,其中最常用的是ApplicationContext接口的实现类。ApplicationContext提供了多种实现,如ClassPathXmlApplicationContextAnnotationConfigApplicationContext等,用于不同的配置方式。

以下是一个简单的示例,展示如何使用ApplicationContext实现IoC:

1. 创建一个简单的Java类:

public class MessageService {private String message;public MessageService() {this.message = "Hello, IoC!";}public String getMessage() {return message;}
}

2. 创建一个Spring配置类:

import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;@Configuration
public class AppConfig {// 使用@Bean注解声明一个Bean,Spring容器会管理它@Beanpublic MessageService messageService() {return new MessageService();}
}

3. 使用IoC容器获取Bean:

import org.springframework.context.ApplicationContext;
import org.springframework.context.annotation.AnnotationConfigApplicationContext;public class MainApp {public static void main(String[] args) {// 创建IoC容器,使用注解配置ApplicationContext context = new AnnotationConfigApplicationContext(AppConfig.class);// 从容器中获取MessageService的实例MessageService messageService = context.getBean(MessageService.class);// 调用getMessage方法System.out.println(messageService.getMessage());}
}

在这个例子中:

  • MessageService类不再由程序员负责创建,而是由Spring容器管理。
  • AppConfig配置类使用了@Bean注解,告诉Spring容器要管理MessageService这个Bean。
  • MainApp类通过ApplicationContext容器获取MessageService的实例,而不是直接实例化。

通过这种方式,IoC容器实现了对对象的创建和依赖关系的控制反转。Spring框架利用IoC的思想,帮助开发者更容易构建松散耦合、可维护和可测试的应用。

什么是DI(依赖注入)?Spring是如何支持依赖注入的?

依赖注入(DI)是什么:

依赖注入是一种设计模式,它是控制反转(IoC)思想的一种具体实现。在依赖注入中,对象的依赖关系不再由对象本身负责,而是由外部容器负责。这样做的好处是降低了组件之间的耦合度,使系统更加灵活、可维护。

在依赖注入中,依赖关系可以通过构造函数、方法参数、或者类的属性进行注入。Spring框架主要通过构造函数注入和属性注入来实现依赖注入。

Spring如何支持依赖注入:

Spring框架提供了多种方式来实现依赖注入,其中最常见的方式包括:

  1. 构造函数注入(Constructor Injection): 通过在类的构造函数中声明需要注入的依赖,Spring容器会在创建Bean的时候通过构造函数将依赖注入。

    public class MyService {private final MyDependency myDependency;public MyService(MyDependency myDependency) {this.myDependency = myDependency;}// Other methods...
    }
    

    在XML配置中:

    <bean id="myService" class="com.example.MyService"><constructor-arg ref="myDependency"/>
    </bean><bean id="myDependency" class="com.example.MyDependency"/>
    
  2. 属性注入(Setter Injection): 通过Setter方法来注入依赖。Spring容器在创建Bean后,通过调用Setter方法将依赖注入到Bean中。

    public class MyService {private MyDependency myDependency;public void setMyDependency(MyDependency myDependency) {this.myDependency = myDependency;}// Other methods...
    }
    

    在XML配置中:

    <bean id="myService" class="com.example.MyService"><property name="myDependency" ref="myDependency"/>
    </bean><bean id="myDependency" class="com.example.MyDependency"/>
    
  3. 接口注入(Interface Injection): 通过实现特定的接口,在接口中定义注入方法,Spring容器通过调用接口的方法完成注入。

    public interface MyServiceInjector {void injectDependency(MyService myService);
    }public class MyService implements MyServiceInjector {private MyDependency myDependency;@Overridepublic void injectDependency(MyService myService) {this.myDependency = myService;}// Other methods...
    }
    

    在XML配置中:

    <bean id="myService" class="com.example.MyService"/>
    <bean id="myServiceInjector" class="com.example.MyServiceInjector"><property name="myService" ref="myService"/>
    </bean>
    

这些方法使得开发者能够在Spring框架中方便地进行依赖注入,实现了对对象之间关系的松散耦合。通过使用依赖注入,Spring框架实现了IoC的思想,提高了代码的可维护性和可测试性。

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

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

相关文章

基于YOLOv8深度学习的高精度车辆行人检测与计数系统【python源码+Pyqt5界面+数据集+训练代码】目标检测、深度学习实战

《博主简介》 小伙伴们好&#xff0c;我是阿旭。专注于人工智能、AIGC、python、计算机视觉相关分享研究。 ✌更多学习资源&#xff0c;可关注公-仲-hao:【阿旭算法与机器学习】&#xff0c;共同学习交流~ &#x1f44d;感谢小伙伴们点赞、关注&#xff01; 《------往期经典推…

介绍一款低代码数据可视化平台

一、前言 随着企业数字化拉开序幕&#xff0c;低代码( Low Code Development)开发的概念开始火起来&#xff0c;即用少量的代码就能开发复杂的业务系统。然后更进一步&#xff0c;由此又催生出一个新的概念&#xff1a;无代码开发( No Code Development)。 低代码和无代码开发平…

Docker单点部署 Elasticsearch + Kibana [8.11.3]

文章目录 一、Elasticsearch二、Kibana三、访问四、其他 Elasticsearch 和 Kibana 版本一般需要保持一致才能一起使用&#xff0c;但是从 8.x.x开始&#xff0c;安全验证不断加强&#xff0c;甚至8.x.x之间的版本安全验证方法都不一样&#xff0c;真的很恼火。 这里记录一次成…

娱乐新拐点:TikTok如何改变我们的日常生活?

在数字时代的浪潮中&#xff0c;社交媒体平台不断涌现&#xff0c;其中TikTok以其独特的短视频内容在全球范围内掀起了一场娱乐革命。本文将深入探讨TikTok如何改变我们的日常生活&#xff0c;从社交互动、文化传播到个人创意表达&#xff0c;逐步改写了娱乐的新篇章。 短视频潮…

go-zero开发入门之gateway深入研究1

创建一个 gateway 示例&#xff1a; // main.go package mainimport ("flag""fmt""gateway/middleware""github.com/zeromicro/go-zero/core/conf""github.com/zeromicro/go-zero/gateway" )var configFile flag.String(&…

idea2023解决右键没有Servlet的问题

复制Servlet Class.java中的文件。 回到文件&#xff0c;然后点击小加号 然后输入刚刚复制的东西&#xff1a; 3. 此时右键有servlet。 4. 然后他让你输入下面两个框&#xff1a; JAVAEE TYPE中输入Servlet Class Name 表示你要创建的Servlet类的名称是什么。自己起名字。然后…

手动添加Git Bash Here到右键菜单(超详细)

通过WindowsR快捷键可以打开“运行窗口”&#xff0c;在“窗口”中输入“regedit”&#xff0c;点击“确定”打开注册表。 依次进入HKEY_CLASSES_ROOT —-》 Directory —-》Background —-》 shell 路径为Computer\HKEY_CLASSES_ROOT\Directory\Background\shell 3.在“s…

Python中Requests的深入了解

Requests的深入了解 基本POST请求&#xff08;data参数&#xff09; 1. 最基本post方法 response requests.post("http://www.baidu.com/", data data)2. 传入data数据 对于 POST 请求来说&#xff0c;我们一般需要为它增加一些参数。那么最基本的传参方法可以…

状态的一致性和FlinkSQL

状态一致性 一致性其实就是结果的正确性。精确一次是指数据有可能被处理多次&#xff0c;但是结果只有一个。 三个级别&#xff1a; 最多一次&#xff1a;1次或0次&#xff0c;有可能丢数据至少一次&#xff1a;1次或n次&#xff0c;出错可能会重试 输入端只要可以做到数据重…

mongo分组查询问题以及mongo根据Date类型查询

一、mongo分组查询 mongo中如果只是根据条件查询数据&#xff0c;则只需要&#xff1a; db.getCollection(表名).find({source:{$eq:5}}) 如果根据字段进行分组查询&#xff0c;那么需要用aggregate传一个数组进行查询&#xff0c;如 db.getCollection(表名).find({ "…

[每周一更]-(第27期):HTTP压测工具之wrk

[补充完善往期内容] wrk是一款简单的HTTP压测工具,托管在Github上,https://github.com/wg/wrkwrk 的一个很好的特性就是能用很少的线程压出很大的并发量. 原因是它使用了一些操作系统特定的高性能 io 机制, 比如 select, epoll, kqueue 等. 其实它是复用了 redis 的 ae 异步事…

Android APP 常见概念与 adb 命令

adb 的概念 adb 即 Android Debug Bridge 。在窗口输入 adb 即可显示帮助文档。adb 实际上就是在后台开启一个 server&#xff0c;会接收 adb 的命令然后帮助管理&#xff0c;控制&#xff0c;查看设备的状态、信息等&#xff0c;是开发、测试 Android 相关程序的最常用手段。…

Centos系统pnpm升级报错 ERR_PNPM_NO_GLOBAL_BIN_DIR

在 CentOS 系统中使用 pnpm i -g pnpm 报错&#xff1a;ERR_PNPM_NO_GLOBAL_BIN_DIR Unable to find the global bin directory&#xff0c;折腾半天终于解决了。 完整报错信息 [rootVM-8 test]# pnpm i -g pnpm Nothing to stop. No server is running for the store at /roo…

linux20day 排序sort 字符处理cut cpu使用占比排序 awk文本数据处理

目录 1、排序sort参数用法排序&#xff08;-n&#xff09;从大到小 倒叙&#xff08;-r&#xff09; cpu使用占比排序&#xff08;ps aux --sort -%cpu&#xff09; 2、截取到某个字符串 cut3、awk处理文本文件用法&#xff1a;打印等于 和不等于 1、排序sort 经常用于排序 参…

Spring 的 @Configuration 和 @Component 注解区别

&#x1f680; 作者主页&#xff1a; 有来技术 &#x1f525; 开源项目&#xff1a; youlai-mall &#x1f343; vue3-element-admin &#x1f343; youlai-boot &#x1f33a; 仓库主页&#xff1a; Gitee &#x1f4ab; Github &#x1f4ab; GitCode &#x1f496; 欢迎点赞…

数据分析的基本步骤

了解过数据分析的概念之后&#xff0c;我们再来说下数据分析的常规步骤。 明确目标 首先我们要确定一个目标&#xff0c;即我们要从数据中得到什么。比如我们要看某个指标A随时间的变化趋势&#xff0c;以期进行简单的预测。 数据收集 当确定了目标之后&#xff0c;就有了取…

js逆向-JS加密破解进阶

目录 一、JS逆向进阶一&#xff1a;破解AES加密 &#xff08;一&#xff09;AES对称加密算法原理 &#xff08;二&#xff09;破解AES加密 &#xff08;三&#xff09;实战&#xff1a;发现报告网 二、JS逆向进阶二&#xff1a;破解RSA加密 &#xff08;一&#xff09;RS…

gRPC 一种现代、开源、高性能的远程过程调用 (RPC) 可以在任何地方运行的框架

背景介绍 gRPC 是一种现代开源高性能远程过程调用 &#xff08;RPC&#xff09; 可以在任何环境中运行的框架。它可以有效地连接服务 在数据中心内和数据中心之间&#xff0c;具有对负载平衡、跟踪、 运行状况检查和身份验证。它也适用于最后一英里 分布式计算&#xff0c;用于…

P20类神经网络训练不起来怎么办?- 批次和动量

什么是batchsmall batch 和 large batch 的比较 &#xff1a; large batch 更快&#xff0c;small batch 在训练集和测试集上效果效果更好动量的意义和作用&#xff1a; 类似于物理上多了一点惯性&#xff0c;防止困在鞍点。 动量是之前所有梯度的加权和。 1. batch 是什么 …

高压电气是什么

高压电气 电工电气百科 文章目录 高压电气前言一、高压电气是什么二、高压电气的类别三、高压电气的作用原理总结前言 高压电气在电力系统中起着重要的作用,它能够将电能有效地输送和分配到各个用户,为社会和工业生产提供稳定可靠的电力供应。然而,高压电气系统也需要注意安…