SPRING面试题

1.Spring中的bean的作用域

1.singleton:唯一bean实例,Spring中的bean默认都是单例的。
2.prototype:每次请求都会创建一个新的bean实例。
3.request:每一次HTTP请求都会产生一个新的bean,该bean仅在当前HTTP request内有效。
4.session:每一次HTTP请求都会产生一个新的bean,该bean仅在当前HTTP session内有效。

2.Spring中的单例bean的线程安全问题

单例bean存在线程问题,主要是因为当多个线程操作同一个对象的时候,对这个对象的非静态成员变量的写操作会存在线程安全问题。
有两种常见的解决方案:
1.在bean对象中尽量避免定义可变的成员变量
2.在类中定义一个ThreadLocal成员变量,将需要的可变成员变量保存在ThreadLocal中

3.Spring中的bean生命周期

 参考:spring中Bean的生命周期

1.实例化 Instantiation:根据配置情况调用 Bean 构造方法或工厂方法实例化 Bean。
2.属性赋值 Populate:利用依赖注入完成 Bean 中所有属性值的配置注入。
3.初始化 Initialization:根据Bean的不同定义,完成不同的初始化。
4.销毁 Destruction:随着容器的销毁而销毁

4.将一个类声明为Spring的bean的注解有哪些

1.@Component注解。通用的注解,可标注任意类为Spring组件。
2.@Repository注解。对应持久层,即Dao层,主要用于数据库相关操作。
3.@Service注解。对应服务层,即Service层,主要涉及一些复杂的逻辑,需要用到Dao层(注入)。
4.@Controller注解。对应Spring MVC的控制层,即Controller层,主要用于接受用户请求并调用Service层的方法返回数据给前端页面。
这些标识的bean,我们可以用@Autowired注解去自动装配

5.Spring 的单例实现原理

Spring框架对单例的支持是采用单例注册表的方式进行实现的,而这个注册表的缓存是HashMap对象,如果配置文件中的配置信息不要求使用单例,Spring会采用新建实例的方式返回对象实例。

6.Spring的内部beans是什么

当bean仅用作另一个bean的属性时,可以将其声明为内部bean。Spring的基于XML的配置元数据提供了bean定义中元素的使用,以便定义所谓的内部bean。内部bean总是匿名的,它们总是作为原型。

7.Spring框架中用到了哪些设计模式

1.工厂设计模式:Spring使用工厂模式通过BeanFactory和ApplicationContext创建bean对象。
2.代理设计模式:Spring AOP功能的实现。
3.单例设计模式:Spring中的bean默认都是单例的。
4.模板方法模式:IOC初始化中refreshContext

8.@Component和@Bean的区别是什么

1.作用对象不同。@Component注解作用于类,而@Bean注解作用于方法。
2.@Component注解通常是通过类路径扫描来自动侦测以及自动装配到Spring容器中(可以使用@ComponentScan)。@Bean注解通常是在标有该注解的方法中定义产生这个bean,告诉Spring这是某个类的实例。
3.@Bean注解比@Component注解的自定义性更强,而且很多地方只能通过@Bean注解来注册bean。比如当引用第三方库的类需要装配到Spring容器的时候,就只能通过@Bean注解来实现。

9.@Autowired 与@Resource的区别

@Autowired与@Resource都可以用来装配bean. 都可以写在字段上,或写在setter方法
@Autowired默认按类型装配,默认情况下必须要求依赖对象必须存在,如果要允许null值,可以设置它的required属性为false,如:@Autowired(required=false) ,如果我们想使用名称装配可以结合@Qualifier注解进行使用,如下:@Autowired () @Qualifier ( "baseDao" )
@Resource默认按照名称进行装配,名称可以通过name属性进行指定,如果没有指定name属性,当注解写在字段上时,默认取字段名进行安装名称查找,如果注解写在setter方法上默认取属性名进行装配。当找不到与名称匹配的bean时才按照类型进行装配。

10.@Component, @Controller, @Repository, @Service 有何区别

@Component:这将 java 类标记为 bean。它是任何 Spring 管理组件的通用构造型。spring 的组件扫描机制现在可以将其拾取并将其拉入应用程序环境中。
@Controller:这将一个类标记为 Spring Web MVC 控制器。标有它的 Bean 会自动导入到 IoC 容器中。
@Service:此注解是组件注解的特化。它不会对 @Component 注解提供任何其他行为。您可以在服务层类中使用 @Service 而不是 @Component,因为它以更好的方式指定了意图。
@Repository:这个注解是具有类似用途和功能的 @Component 注解的特化。它为 DAO 提供了额外的好处。它将 DAO 导入 IoC 容器,并使未经检查的异常有资格转换为 Spring DataAccessException。

11.解释自动装配的各种模式

参考:SpringBoot(二)原理剖析:AutoConfiguration原理  

当 bean 在 Spring 容器中组合在一起时,它被称为装配或 bean 装配。 Spring 容器需要知道需要什么 bean 以及容器应该如何使用依赖注入来将 bean 绑定在一起,同时装配 bean。
自动装配提供五种不同的模式供Spring容器用来自动装配beans之间的依赖注入: no:默认的方式是不进行自动装配,通过手工设置ref 属性来进行装配bean。 byName:通过参数名自动装配,Spring容器查找beans的属性,这些beans在XML配置文件中被设置为byName。之后容器试图匹配、装配和该bean的属性具有相同名字的bean。 byType:通过参数的数据类型自动自动装配,Spring容器查找beans的属性,这些beans在XML配置文件中被设置为byType。之后容器试图匹配和装配和该bean的属性类型一样的bean。如果有多个bean符合条件,则抛出错误。 constructor:这个同byType类似,不过是应用于构造函数的参数。如果在BeanFactory中不是恰好有一个bean与构造函数参数相同类型,则抛出一个严重的错误。 autodetect:如果有默认的构造方法,通过 construct的方式自动装配,否则使用 byType的方式自动装配。

12.SpringIOC理解

参考:SpringBoot(三)原理剖析:IOC原理 

IOC就是控制反转,指创建对象的控制权转移给Spring框架进行管理,并由Spring根据配置文件去创建实例和管理各个实例之间的依赖关系
DI依赖注入,和控制反转是同一个概念的不同角度的描述,即 应用程序在运行时依赖IoC容器来动态注入对象需要的外部依赖。 最直观的表达就是,以前创建对象的主动权和时机都是由自己把控的,IOC让对象的创建不用去new了,可以由spring自动生产,使用java的反射机制,根据配置文件在运行时动态的去创建对象以及管理对象,并调用对象的方法的。

13.有哪些不同类型的IOC(依赖注入)方式

构造器依赖注入:构造器依赖注入通过容器触发一个类的构造器来实现的,该类有一系列参数,每个参数代表一个对其他类的依赖。
Setter方法注入:Setter方法注入是容器通过调用无参构造器或无参static工厂方法实例化bean之后,调用该bean的setter方法,即实现了基于setter的依赖注入。
构造函数注入setter 注入
没有部分注入 有部分注入
不会覆盖 setter 属性 会覆盖 setter 属性
任意修改都会创建一个新实例 任意修改不会创建一个新实例
适用于设置很多属性 适用于设置少量属性

14.Spring容器的启动流程

参考:SpringBoot(三)原理剖析:IOC原理 

初始化Spring容器,决定创建哪种类型的容器:creatApplicationContext
为容器设置环境信息,记录启动信息,并向容器中注册指定类的单例,包含启动类:prepareContext
设置容器状态、初始化属性,监听事件、剩余的Bean以及Bean工厂的后置处理:refreshContext

15.BeanFactory和ApplicationContext有什么区别

参考:SpringBoot(三)原理剖析:IOC原理 

BeanFactory和ApplicationContext是Spring的两大核心接口,都可以当做Spring的容器。
BeanFactory是Spring里面最底层的接口,定义了IoC的基本功能,包含了各种Bean的定义、加载、实例化,依赖注入和生命周期管理。ApplicationContext接口作为BeanFactory的子类,除了提供BeanFactory所具有的功能外,还提供了更完整的框架功能
BeanFactroy采用的是延迟加载形式来注入Bean的,只有在使用到某个Bean时(调用getBean()),才对该Bean进行加载实例化。ApplicationContext,它是在容器启动时,一次性创建了所有的Bean。
ApplicationContext启动后预载入所有的单实例Bean,所以在运行的时候速度比较快,因为它们已经创建好了。相对于BeanFactory,ApplicationContext 唯一的不足是占用内存空间,当应用程序配置Bean较多时,程序启动较慢。

16.Spring如何解决循环依赖问题

循环依赖问题在Spring中主要有三种情况:
(1)通过构造方法进行依赖注入时产生的循环依赖问题。
(2)通过setter方法进行依赖注入且是在多例(原型)模式下产生的循环依赖问题。
(3)通过setter方法进行依赖注入且是在单例模式下产生的循环依赖问题。
在Spring中,只有第(3)种方式的循环依赖问题被解决了,其他两种方式在遇到循环依赖问题时都会产生异常。这是因为:
第一种构造方法注入的情况下,在new对象的时候就会堵塞住了,其实也就是”先有鸡还是先有蛋“的历史难题
第二种setter方法(多例)的情况下,每一次getBean()时,都会产生一个新的Bean,如此反复下去就会有无穷无尽的Bean产生了,最终就会导致OOM问题的出现。
Spring在单例模式下的setter方法依赖注入引起的循环依赖问题,主要是通过二级缓存和三级缓存来解决的,其中三级缓存是主要功臣。解决的核心原理就是:在对象实例化之后,依赖注入之前,Spring提前暴露的Bean实例的引用在第三级缓存中进行存储

17.SpringAOP怎么开启

 参考:SpringBoot(四)原理剖析:AOP原理 

AopAutoConfiguration类支持默认开启

18.SpringAOP基本概念

参考:SpringBoot(四)原理剖析:AOP原理 

通知(Advice): AOP 框架中的增强处理。通知描述了切面何时执行以及如何执行增强处理;
连接点(Join Point): 连接点表示应用执行过程中能够插入切面的一个点。在 Spring AOP 中,连接点总是方法的调用,可以说目标对象中的方法就是一个连接点;
切点(Pointcut): 就是连接点的集合;对应Spring中的@Pointcut注解;
切面(Aspect): 切面是通知和切点的结合;对应Spring中的注解@Aspect修饰的一个类;
目标对象(Target object):即被代理的对象;    
代理对象(AOP proxy):包含了目标对象的代码和增强后的代码的那个对象;

19.Spring AOP中的动态代理

参考反射机制

主要有两种方式,JDK动态代理和CGLIB动态代理
JDK动态代理:只提供接口的代理,不支持类的代理,要求被代理类实现接口。如果被代理类没有实现接口,那么Spring AOP会选择使用CGLIB来动态代理目标类。
CGLIB(Code Generation Library):是一个代码生成的类库,可以在运行时动态的生成指定类的一个子类对象,并覆盖其中特定方法并添加增强代码,从而实现AOP。CGLIB是通过继承的方式做的动态代理,因此如果某个类被标记为final,那么它是无法使用CGLIB做动态代理的。

20.Spring通知(Advice)有哪些类型

参考:SpringBoot(四)原理剖析:AOP原理

Before :前置通知,在连接点方法前调用;对应Spring中@Before注解;
After :后置通知,在连接点方法后调用;对应Spring中的@After注解;
AfterReturning:返回通知,在连接点方法执行并正常返回后调用,要求连接点方法在执行过程中没有发生异常;对应Spring中的@AfterReturning注解;
AfterThrowing:异常通知,当连接点方法异常时调用;对应Spring中的@AfterThrowing注解;
Around:环绕通知,它将覆盖原有方法,但是允许你通过反射调用原有方法;对应Spring中的@Around注解;

21.Spring事务中的隔离级别和传播行为

参考:SpringBoot(五)原理剖析:Transaction原理 

22.Spring事务的实现方式和实现原理

参考:SpringBoot(五)原理剖析:Transaction原理 

Spring事务的本质其实就是数据库对事务的支持,没有数据库的事务支持,spring是无法提供事务功能的。Spring只提供统一事务管理接口,具体实现都是由各数据库自己实现,数据库事务的提交和回滚是通过binlog或者undo log实现的。
Spring会在事务开始时,根据当前环境中设置的隔离级别,调整数据库隔离级别,由此保持一致。
划分处理单元——IoC:由于spring解决的问题是对单个数据库进行局部事务处理的,具体的实现首先用spring中的IoC划分了事务处理单元。并且将对事务的各种配置放到了ioc容器中(设置事务管理器,设置事务的传播特性及隔离机制)。
AOP拦截需要进行事务处理的类:Spring事务处理模块是通过AOP功能来实现声明式事务处理的,具体操作(比如事务实行的配置和读取,事务对象的抽象),用TransactionProxyFactoryBean接口来使用AOP功能,生成proxy代理对象,通过TransactionInterceptor完成对代理方法的拦截,将事务处理的功能编织到拦截的方法中。读取ioc容器事务配置属性,转化为spring事务处理需要的内部数据结构(TransactionAttributeSourceAdvisor),转化为TransactionAttribute表示的数据对象。
对事务处理实现(事务的生成、提交、回滚、挂起):spring委托给具体的事务处理器实现。实现了一个抽象和适配。适配的具体事务处理器:DataSource数据源支持、hibernate数据源事务处理支持、JDO数据源事务处理支持,JPA、JTA数据源事务处理支持。这些支持都是通过设计PlatformTransactionManager、AbstractPlatforTransaction一系列事务处理的支持。 为常用数据源支持提供了一系列的TransactionManager。

--------------------------------------------Spirng Cloud--------------------------------------------

1.SpringCloud和Dubbo区别

(1)服务调用方式:dubbo是RPC;springcloud Rest Api
(2)注册中心:dubbo 是zookeeper;springcloud是eureka,也可以是zookeeper
(3)服务网关:dubbo本身没有实现,只能通过其他第三方技术整合;springcloud有Zuul、springcloudgateway作为路由网关

2.Eureka和ZooKeeper区别

参见:SpringCloud(二) 微服务架构-服务注册与发现 

1.ZooKeeper保证的是CP,Eureka保证的是AP
ZooKeeper在选举期间注册服务瘫痪,虽然服务最终会恢复,但是选举期间不可用的;Eureka各个节点是平等关系,只要有一台Eureka就可以保证服务可用,而查询到的数据并不是最新的
2.ZooKeeper有Leader和Follower角色,Eureka各个节点平等
3.ZooKeeper采用过半数存活原则,Eureka采用自我保护机制解决分区问题

3.什么是Hystrix

防雪崩利器,具备服务降级,服务熔断,依赖隔离,监控(Hystrix Dashboard)

4.springcloud断路器作用

当一个服务调用另一个服务由于网络原因或自身原因出现问题,调用者就会等待被调用者的响应 当更多的服务请求到这些资源导致更多的请求等待,发生连锁效应(雪崩效应).
完全打开状态:一段时间内 达到一定的次数无法调用 并且多次监测没有恢复的迹象 断路器完全打开 那么下次请求就不会请求到该服务
半开:短时间内有恢复迹象 断路器会将部分请求发给该服务,正常调用时 断路器关闭
关闭:当服务一直处于正常状态 能正常调用
原文地址:https://www.cnblogs.com/ryjJava/p/14421475.html