• Spring必背面试题


    1.什么是BeanDefinition?

    BeanDefinition表示Bean定义,
    Spring根据BeanDefinition来创建Bean对象,
    BeanDefinition有很多的属性用来描述Bean,
    BeanDefinition是Spring中非常核心的概念。

    BeanDefinition中重要的属性:
    beanClass:表示一个bean的类型,比如UserService.class、OrderService.class,Spring在创建Bean的过程中会根据此属性来实例化得到对象。
    scope:表示一个bean的作用域,比如:scope等于singleton,该bean就是一个单例Bean; scope等于prototype,该bean就是一个原型Bean。
    isLazy:表示一个bean是不是需要懒加载,原型bean的isLazy属性不起作用,懒加载的单例bean,会在第一次getBean的时候生成该bean,非懒加载的单例bean,则会在Spring启动过程中直接生成好。
    dependsOn:表示一个bean在创建之前所依赖的其他bean,在一个bean创建之前,它所依赖的这些bean得先全部创建好。
    primary:表示一个bean是主bean,在Spring中一个类型可以有多个bean对象,在进行依赖注入时,如果根据类型找到了多个bean,此时会判断这些bean中是否存在一个主bean,如果存在,则直接将这个bean注入给属性。
    initMethodName:表示一个bean的初始化方法,一个bean的生命周期过程中有一个步骤叫初始化,Spring会在这个步骤中去调用bean的初始化方法,初始化逻辑由程序员自己控制,表示程序员可以自定义逻辑对bean进行加工。

    @Component、@Bean、 这些都会解析为BeanDefinition对象

    2.什么是BeanFactory?

    BeanFactory是一种“Spring容器”,
    BeanFactory翻译过来就是Bean工厂,
    顾名思义,它可以用来创建Bean、获取Bean,
    BeanFactory是Spring中非常核心的组件。

    BeanDefiniton、BeanFactory、Bean对象的关系
    BeanFactory将利用BeanDefinition来生成Bean对象,
    BeanDefinition相当于BeanFactory的原材料,
    Bean对象就相当于BeanFactory所生产出来的产品

    BeanFactory的核心子接口和实现类
    ListableBeanFactory
    ConfigurableBeanFactory
    AutowireCapableBeanFactory
    AbstractBeanFactory
    DefaultListableBeanFactory

    DefaultListableBeanFactory的功能
    支持单例Bean、支持Bean别名、支持父子BeanFactory、支持Bean类型转化、支持Bean后置处理、支持FactoryBean、支持自动装配,等等。

    3.什么是Bean生命周期

    Bean生命周期描述的是Spring中一个Bean创建过程和销毁过程中所经历的步骤,其中Bean创建过程是重点。
    程序员可以利用Bean生命周期机制对Bean进行自定义加工。

    Bean的创建生命周期 核心步骤,按顺序
    1.BeanDefinition:Bean定义。它定义了某个Bean的类型,Spring就是利用BeanDefinition来创建Bean的,比如需要利用BeanDefinition中beanClass属性确定Bean的类型,从而实例化出来对象。

    2.构造方法推断:选出一个构造方法。一个Bean中可以有多个构造方法,此时就需要Spring来判断到底使用哪个构造方法。通过构造方法推断之后确定一个构造方法后,就可以利用构造方法实例化得到一个对象了。

    3.实例化:构造方法反射得到对象。通过构造方法反射得到一个实例化对象,在Spring中,可以通过BeanPostProcessor机制对实例化进行干预。

    4.属性填充:给属性进行自动填充。实例化所得到的对象,是“不完整”的对象,“不完整”的意思是对该对象中的某些属性还没有进行属性填充,也就是Spring还没有自动给某些属性赋值,属性填充就是我们通常说的自动注入、依赖注入。

    5.初始化:对其他属性赋值、校验。在一个对象的属性填充之后,Spring提供了初始化机制,程序员可以利用初始化机制对Bean进行自定义加工,比如可以利用InitializingBean接口来对Bean中的其他属性进行赋值,或对Bean中的某些属性进行校验。

    6.初始化后:AOP、生成代理对象。初始化后是Bean创建生命周期中最后一个步骤,我们常说的AOP机制,就是在这个步骤中通过BeanPostProcessor机制实现的,初始化之后得到的对象才是真正的Bean对象。

    4.@Autowired是如何工作的?

    @Autowired表示某个属性是否需要进行依赖注入,可以写在属性和方法上。注解中的required属性默认为true,表示如果没有对象可以注入给属性则抛异常。

    1.加在属性上
    @Autowired加在某个属性上,Spring再进行Bean的生命周期过程中,在属性填充这一步,会基于实例化出来的对象,对该对象中加了@Autowired的属性自动给属性赋值。

    Spring会先根据属性的类型去Spring容器中找出该类型所有的Bean对象,如果找出来多个,则再根据属性的名字从多个中再确定一个。
    如果required属性为true,并且根据属性信息找不到对象,则直接抛出异常。

    2.加在方法上
    当@Autowired注解写在某个方法上是,Spring在Bean生命周期的属性填充阶段,会根据方法的参数类型、参数名字从Spring容器找到对象当作方法入参,自动反射调用该方法。

    3.加在构造方法上
    @Autowired加在构造方法上时,Spring会在推断构造方法阶段,选择该构造方法来进行实例化,在反射调用构造方法之前,会先根据构造方法参数类型、参数名从Spring容器中找到Bean对象,当做构造方法入参。

    5.@Resource是如何工作的?

    @Resource注解与@Autowired类似,也是用来进行依赖注入的,@Resource是Java层面所提供的注解,@Autowired是Spring所提供的注解,它们依赖注入的底层实现逻辑也不同。

    @Resource注解中有一个name属性,针对name属性是否有值,@Resource的依赖注入底层流程是不同的。

    1.name属性有值
    @Resource如果name属性有值,那么Spring会直接根据所指定的name值去Spring容器找Bean对象,如果找到了则成功,如果没有找到,则报错。

    2.name属性没有值
    如果@Resource中的name属性没有值,则:
    一、先判断该属性名字在Spring容器中是否存在Bean对象。
    二、如果存在,则成功找到Bean对象进行注入。
    三、如果不存在,则根据属性类型去Spring容器找Bean对象,找到一个则进行注入。

    6.@Value是如何工作的?

    @Value注解和@Resource、@Autowired类似,也是用来对属性进行依赖注入的,只不过@Value是用来从Properties文件中来获取值的,并且@Value可以解析SpEL(Spring表达式)。

    1.@Value(“识时务者-HJJ”)
    直接将字符串“识时务者-HJJ”赋值给属性,如果属性类型不是String,或无法进行类型转化,则报错。

    2.@Value(" 识时务者 − H J J " ) 将会把 {识时务者-HJJ}") 将会把 识时务者HJJ")将会把{}中的字符串当做key,从Properties文件中找出对应的value赋值给属性,如果没找到,则会把“${识时务者-HJJ}”当做普通字符串注入给属性。

    3.@Value(“#{识时务者-HJJ}”)
    会将#{}中的字符串当做Spring表达式进行解析,Spring会把“识时务者-HJJ”当做beanName,并从Spring容器中找对应bean,如果找到则进行属性注入,没找到则报错。

    7.什么是FactoryBean?

    FactoryBean是Spring所提供的一种较灵活的创建Bean的方式,可以通过实现FactoryBean接口中的getObject()方法来返回一个对象,这个对象就是最终的Bean对象。

    1.FactoryBean接口中的方法
    一、Object getObject():返回的是Bean对象
    二、boolean isSingleton():返回的是是否单例Bean对象
    三、Class getObjectType():返回的是Bean对象的类型

    @Component("识时务者-HJJ")
    public class LycFactoryBean implements FactoryBean {
        
        @Override
        // Bean对象
        public Object getObject() throws Exception {
            return new User();
        }
    
        @Override
        // Bean对象的类型
        public Class<?> getObjectType() {
            return User.class;
        }
    
        @Override
        // 所定义的Bean是单例还是原型
        public boolean isSingleton() {
            return true;
        }
    }
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18
    • 19
    • 20
    • 21

    2.FactoryBean的特殊点
    上述代码,实际上对应了两个Bean对象:
    一、beanName为“识时务者-HJJ”,bean对象为getObject方法所返回的User对象。
    二、beanName为“&识时务者-HJJ”,bean对象为LycFactoryBean类的实例对象。

    3.混淆
    FactoryBean对象本身也是一个Bean,同时它相当于一个小型工厂,可以生产出另外的Bean。
    BeanFactory是一个Spring容器,是一个大型工厂,它可以生产出各种各样的Bean。

    FactoryBean机制被广泛的应用在Spring内部和Spring与第三方框架或组件的整合过程中。

    8.什么是ApplicationContext?

    ApplicationContext是比BeanFactory更加强大的Spring容器,它既可以创建bean、获取bean、还支持国际化、事件广播、获取资源等BeanFactory不具备的功能。

    ApplicationContext所继承的接口:
    1.EnvironmentCapable:ApplicationContext继承了这个接口,表示拥有了获取环境变量的功能,可以通过ApplicationContext获取操作系统环境变量和JVM环境变量。

    2.ListableBeanFactory:ApplicationContext继承了这个接口,就拥有了获取所有beanNames、判断某个beanName是否存在beanDefinition对象、统计BeanDefinition个数、获取某个类型对应的所有beanNames等功能。

    3.HierarchicalBeanFactory:ApplicationContext继承了这个接口,就拥有了获取父BeanFactory、判断某个name是否存在bean对象的功能。

    4.MessageSource:ApplicationContext继承了这个接口,就拥有了国际化功能,比如可以直接利用MessageSource对象获取某个国际化资源(比如不同国家语言所对应的字符)

    5.ApplicationEventPublisher:ApplicationContext继承了这个接口,就拥有了事件发布功能,可以发布事件,这是ApplicationContext相对于BeanFactory比较突出、常用的功能。

    6.ResourcePatternResolver:ApplicationContext继承了这个接口,就拥有了加载并获取资源的功能,这里的资源可以是文件,图片等某个URL资源都可以。

    9.什么是BeanPostProcessor?

    BeanPostProcessor是Spring所提供的一种扩展机制,可以利用该机制对Bean进行定制化加工,在Spring底层源码实现中,也广泛的用到了该机制,BeanPostProcessor通常也叫做Bean后置处理器。

    BeanPostProcessor在Spring中是一个接口,我们定义一个后置处理器,就是提供一个类实现该接口,在Spring中还存在一些接口继承了BeanPostProcessor,这些子接口是在BeanPostProcessor的基础上增加了一些其他的功能。

    BeanPostProcessor中的方法:
    1.postProcessBeforeInitialization():初始化前方法,表示可以利用这个方法来对Bean在初始化前进行自定义加工。
    2.postProcessAfterInitialization():初始化后方法,表示可以利用这个方法来对Bean在初始化后进行自定义加工。

    InstantiationAwareBeanPostProcessor是BeanPostProcessor的一个子接口,其中有三个方法
    1.postProcessBeforeInstantiation():实例化前
    2.postProcessAfterInstantiation():实例化后
    3.postProcessProperties():属性注入后

    10.AOP是如何工作的?

    1.AOP是什么?
    AOP就是面向切面编程,是一种非常适合在无需修改业务代码的前提下,对某个或某些业务增加统一的功能,比如日志记录、权限控制、事务管理等,能很好的使得代码解耦,提高开发效率。

    2.AOP中的核心概念:

    一、Advice:Advice可以理解为通知、建议,在Spring中通过定义Advice来定义代理逻辑。

    二、Pointcut:Pointcut是切点,表示Advice对应的代理逻辑应用在哪个类、哪个方法上。

    三、Advisor:Advisor等于Advice+Pointcut,表示代理逻辑和切点的一个整体,程序员可以通过定义或封装一个Advisor,来定义切点和代理逻辑。

    四、Weaving:Weaving表示织入,将Advice代理逻辑在源代码级别嵌入到切点的过程,就叫做织入。

    五、Target:Target表示目标对象,也就是被代理对象,在AOP生成的代理对象中会持有目标对象。

    六、Join Point:Join Point表示连接点,在Spring AOP中,就是方法的执行点。

    3.AOP的工作原理:
    AOP是发生在Bean的生命周期过程中的:

    一、Spring生成bean对象时,先实例化出来一个对象,也就是target对象

    二、再对target对象进行属性填充

    三、在初始化后步骤中,会判断target对象有没有对应的切面

    四、如果又切面,就表示当前target对象需要进行AOP

    五、通过CGlib或JDK动态代理机制生成一个代理对象,作为最终的bean对象

    六、代理对象中有一个target属性指向了target对象

    此面试题是基于 震惊!京东大佬居然用动画的形式把spring讲得这么透彻,谁看谁知道 总结的,有兴趣的可以去B站看视频学习。

  • 相关阅读:
    MySQL学习笔记(九)MVCC
    经验之谈:内存泄露的原因以及分析
    如何运用API接口获取淘宝1688京东商品数据:从入门到实践
    探究Springboot自动装配原理
    前端回流与重绘:概念及触发条件
    基于TLS的抓包内容分析解决方法
    vue 分段进度条组件
    【LeetCode】1662.检查两个字符串数组是否相等
    首份中国企业敏捷实践白皮书发布| 附完整下载
    springboot+小区公共停车位管理 毕业设计-附源码201517
  • 原文地址:https://blog.csdn.net/weixin_59262008/article/details/126796180