Spring中Bean的生命周期及源码详解

Spring Bean生命周期源码详解 之后child需要根据BeanDefinition来生成Bean对象之前,需要进行BeanDefinition的合并,得到完整的child的BeanDefinition,也就是RootBeanDefinition。我们知道BeanPostProcessor接口的作用是在bean初始化前和初始化后执行一些方法,Spring提供了该接口的子接口来进行实例化前后执行的一些方法。可以在这个步骤中,对Bean最终进行处理,Spring中的AOP就是基于初始化后实现的,初始化后返回的对象才是最终的Bean对象。 阅读详情

Spring Bean 实例化步骤

  • 推断构造方法
  • 通过构造方法创建对象
  • 填充属性,即依赖注入
  • 处理ApplicationContextAware接口的回调,即处理ApplicationContextAware接口的setApplicationContext方法
  • 初始化前,即处理@PostConstruct注解的方法
  • 初始化,即处理InitializingBean接口的afterPropertiesSet方法
  • 初始化后,AOP。

代码验证

BeanInitTest实现了ApplicationContextAware、InitializingBean 接口,且用 @PostConstruct注解声明了初始化前方法,声明了一个切面AopAspectTest,使得BeanInitTest是AOP代理对象。

如果在afterPropertiesSet、setApplicationContext、beforeInit方法上打断点,调试启动,会发现依次顺序进入setApplicationContext、beforeInit、afterPropertiesSet方法。

@Service
public class BeanInitTest implements ApplicationContextAware, InitializingBean {

    @Override
    public void afterPropertiesSet() throws Exception {
        System.out.println("初始化");
    }

    @Override
    public void setApplicationContext(ApplicationContext applicationContext) throws BeansException {
        System.out.println("ApplicationContextAware 回调方法");
    }
    @PostConstruct
    private void beforeInit(){
        System.out.println("初始化前");
    }
}
@Component
@Aspect
public class AopAspectTest {
    @Pointcut(" execution (* com.ludk.weixin.service.BeanInitTest.*(..))")
    public void pointCut(){}

    @Before("pointCut()")
    public void cutBefore(){
        System.out.println("切面方法前");
    }

}

代码调试验证

断点选择

在如图所示处打断点,并加上条件beanName.equals(“beanInitTest”),只观察该bean对象实例化,然后调试启动SpringBoot项目在这里插入图片描述

调试观察

进入断点后,如下图所示,左下角是代码调用的堆栈信息,可以看到代码的来源,beanName确实是想监控的bean名称beanInitTest
在这里插入图片描述

创建bean的代码分析并验证

org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.doCreateBean(String beanName, RootBeanDefinition mbd, @Nullable Object[] args)throws BeanCreationException

protected Object doCreateBean(String beanName, RootBeanDefinition mbd, @Nullable Object[] args)
			throws BeanCreationException {

		// Instantiate the bean.
		//创建Bean的时候,会将Bean包装成一个BeanWrapper
		BeanWrapper instanceWrapper = null;
		if (mbd.isSingleton()) {
			instanceWrapper = this.factoryBeanInstanceCache.remove(beanName);
		}
		if (instanceWrapper == null) {
			//创建Bean实例,里面包含推断构造方法,并根据构造方法利用反射实例化Bean对象
			instanceWrapper = createBeanInstance(beanName, mbd, args);
		}
		Object bean = instanceWrapper.getWrappedInstance();
		Class<?> beanType = instanceWrapper.getWrappedClass();
		if (beanType != NullBean.class) {
			mbd.resolvedTargetType = beanType;
		}

		// Allow post-processors to modify the merged bean definition.
		synchronized (mbd.postProcessingLock) {
			if (!mbd.postProcessed) {
				try {
					applyMergedBeanDefinitionPostProcessors(mbd, beanType, beanName);
				}
				catch (Throwable ex) {
					throw new BeanCreationException(mbd.getResourceDescription(), beanName,
							"Post-processing of merged bean definition failed", ex);
				}
				mbd.postProcessed = true;
			}
		}

		// Eagerly cache singletons to be able to resolve circular references
		// even when triggered by lifecycle interfaces like BeanFactoryAware.
		boolean earlySingletonExposure = (mbd.isSingleton() && this.allowCircularReferences &&
				isSingletonCurrentlyInCreation(beanName));
		if (earlySingletonExposure) {
			if (logger.isTraceEnabled()) {
				logger.trace("Eagerly caching bean '" + beanName +
						"' to allow for resolving potential circular references");
			}
			//将对象工厂放入到Spring的三级缓存中
			addSingletonFactory(beanName, () -> getEarlyBeanReference(beanName, mbd, bean));
		}

		// Initialize the bean instance.
		Object exposedObject = bean;
		try {
			//填充属性,也就是依赖注入
			populateBean(beanName, mbd, instanceWrapper);
			//这里会处理ApplicationContextAware接口的回调、执行初始化前(@PostConstruct注解标注的方法)、初始化(InitializingBean接口方法)、初始化后的操作(AOP代理对象生成)
			exposedObject = initializeBean(beanName, exposedObject, mbd);
		}
		catch (Throwable ex) {
			if (ex instanceof BeanCreationException && beanName.equals(((BeanCreationException) ex).getBeanName())) {
				throw (BeanCreationException) ex;
			}
			else {
				throw new BeanCreationException(
						mbd.getResourceDescription(), beanName, "Initialization of bean failed", ex);
			}
		}

		if (earlySingletonExposure) {
			Object earlySingletonReference = getSingleton(beanName, false);
			if (earlySingletonReference != null) {
				if (exposedObject == bean) {
					exposedObject = earlySingletonReference;
				}
				else if (!this.allowRawInjectionDespiteWrapping && hasDependentBean(beanName)) {
					String[] dependentBeans = getDependentBeans(beanName);
					Set<String> actualDependentBeans = new LinkedHashSet<>(dependentBeans.length);
					for (String dependentBean : dependentBeans) {
						if (!removeSingletonIfCreatedForTypeCheckOnly(dependentBean)) {
							actualDependentBeans.add(dependentBean);
						}
					}
					if (!actualDependentBeans.isEmpty()) {
						throw new BeanCurrentlyInCreationException(beanName,
								"Bean with name '" + beanName + "' has been injected into other beans [" +
								StringUtils.collectionToCommaDelimitedString(actualDependentBeans) +
								"] in its raw version as part of a circular reference, but has eventually been " +
								"wrapped. This means that said other beans do not use the final version of the " +
								"bean. This is often the result of over-eager type matching - consider using " +
								"'getBeanNamesForType' with the 'allowEagerInit' flag turned off, for example.");
					}
				}
			}
		}

		// Register bean as disposable.
		try {
			registerDisposableBeanIfNecessary(beanName, bean, mbd);
		}
		catch (BeanDefinitionValidationException ex) {
			throw new BeanCreationException(
					mbd.getResourceDescription(), beanName, "Invalid destruction signature", ex);
		}

		return exposedObject;
	}

对象创建

doCreateBean的方法中对象创建的代码如下:

if (instanceWrapper == null) {
			instanceWrapper = createBeanInstance(beanName, mbd, args);
		}

org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.createBeanInstance(String beanName, RootBeanDefinition mbd, @Nullable Object[] args)方法参数

  • String beanName:bean名称
  • RootBeanDefinition mbd:bean的定义
  • @Nullable Object[] args:构造方法的参数

根据上面的三个参数推断出构造方法,利用java反射创建对象,相当于new了一个对象。

依赖注入

doCreateBean方法中依赖注入的代码如下:

populateBean(beanName, mbd, instanceWrapper);

org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.populateBean(String beanName, RootBeanDefinition mbd, @Nullable BeanWrapper bw)方法参数

  • String beanName:bean名称
  • RootBeanDefinition mbd:bean的定义
  • @Nullable BeanWrapper bw:bean实例的包装类

依赖注入就是属性填充。上一步只是实例化了对象,对象中属性是null需要调用populateBean方法填充属性。

处理回调、初始化前、初始化、初始化后

doCreateBean方法中Bean初始化前、初始化、初始化后的代码如下:

exposedObject = initializeBean(beanName, exposedObject, mbd);

三个方法均打上断点,监控方法的调用链
在这里插入图片描述
方法依次进入ApplicationContextAware接口的setApplicationContext方法、InitializingBean接口的afterPropertiesSet方法、@PostConstruct注解注释的beforeInit方法,进入断点后同时观察左下角的方法调用链,分析代码。
在这里插入图片描述
org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory#initializeBean(java.lang.String, java.lang.Object, org.springframework.beans.factory.support.RootBeanDefinition)是初始化bean的方法,里面主要包含初始化前、初始化、初始化后三个步骤。

protected Object initializeBean(String beanName, Object bean, @Nullable RootBeanDefinition mbd) {
		if (System.getSecurityManager() != null) {
			AccessController.doPrivileged((PrivilegedAction<Object>) () -> {
				invokeAwareMethods(beanName, bean);
				return null;
			}, getAccessControlContext());
		}
		else {
			invokeAwareMethods(beanName, bean);
		}

		Object wrappedBean = bean;
		if (mbd == null || !mbd.isSynthetic()) {
			//处理Aware接口的回调,其中包括ApplicationContextAware接口的setApplicationContext方法的执行
			//初始化前
			//都是用BeanProcess的前置处理方法实现的
			wrappedBean = applyBeanPostProcessorsBeforeInitialization(wrappedBean, beanName);
		}

		try {
			//初始化 ,InitializingBean接口的afterPropertiesSet方法
			invokeInitMethods(beanName, wrappedBean, mbd);
		}
		catch (Throwable ex) {
			throw new BeanCreationException(
					(mbd != null ? mbd.getResourceDescription() : null),
					beanName, "Invocation of init method failed", ex);
		}
		if (mbd == null || !mbd.isSynthetic()) {
			//初始化后,包括AOP
			wrappedBean = applyBeanPostProcessorsAfterInitialization(wrappedBean, beanName);
		}

		return wrappedBean;
	}

处理Aware回调

wrappedBean = applyBeanPostProcessorsBeforeInitialization(wrappedBean, beanName);

getBeanPostProcessors()获取Bean处理器时,有个
org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory#applyBeanPostProcessorsBeforeInitialization

@Override
	public Object applyBeanPostProcessorsBeforeInitialization(Object existingBean, String beanName)
			throws BeansException {

		Object result = existingBean;
		for (BeanPostProcessor processor : getBeanPostProcessors()) {
			//通过Bean的处理器,调用前置方法实现
			Object current = processor.postProcessBeforeInitialization(result, beanName);
			if (current == null) {
				return result;
			}
			result = current;
		}
		return result;
	}

BeanPostProcessor 是Bean的处理器,是、在容器初始化时对 bean 的创建过程进行扩展和自定义的接口。getBeanPostProcessors()方法获取各种Bean处理器,遍历调用前置方法,执行Bean初始化前的操作。

调试代码中是通过ApplicationContextAwareProcessor处理器,调用postProcessBeforeInitialization前置方法,就会执行到Bean对象ApplicationContextAware接口的setApplicationContext方法。

初始化前

wrappedBean = applyBeanPostProcessorsBeforeInitialization(wrappedBean, beanName);

getBeanPostProcessors()获取Bean处理器时,有个CommonAnnotationBeanPostProcessor处理器,该处理器继承了InitDestroyAnnotationBeanPostProcessor处理器。

CommonAnnotationBeanPostProcessor的postProcessBeforeInstantiation实现是空的,因此执行父类InitDestroyAnnotationBeanPostProcessor的postProcessBeforeInitialization方法,最终执行到@PostConstruct注解标注的方法。调用链路如下:
在这里插入图片描述

初始化

invokeInitMethods(beanName, wrappedBean, mbd);

通过下面的代码调用
在这里插入图片描述
调用链路如下:
在这里插入图片描述

初始化后

wrappedBean = applyBeanPostProcessorsAfterInitialization(wrappedBean, beanName);

getBeanPostProcessors()获取Bean处理器时,有个AnnotationAwareAspectJAutoProxyCreator处理器,它及它的父类均没有实现postProcessAfterInitialization方法,最后只能执行org.springframework.aop.framework.autoproxy.AbstractAutoProxyCreator#postProcessAfterInitialization

@Override
	public Object postProcessAfterInitialization(@Nullable Object bean, String beanName) {
		if (bean != null) {
			Object cacheKey = getCacheKey(bean.getClass(), beanName);
			if (this.earlyProxyReferences.remove(cacheKey) != bean) {
				//这里生成了AOP的代理对象
				return wrapIfNecessary(bean, beanName, cacheKey);
			}
		}
		return bean;
	}

调用链路如下:
在这里插入图片描述

需要注意的是,如果是循环依赖的情况,是根据三级缓存中的对象工厂,创建AOP代理对象的。

TI C2000 , .cmd文件,.TI.ramfunc,将程序分配为在RAM中运行/Flash运行的配置方法和原理讲解,(如28375S ,280049,28335等等芯片) 1 基础知识讲解 1.1 在RAM中运行还是在flash中运行指的是什么? 1.1.1 背景:程序编译完之后生成的.bin文件,.bin文件中包含代码段,代码段中全是汇编指令,而汇编指令中包含多个函数,各函数头的地址不同,如存在A函数和B函数,假设RAM地址区间是0x0000-0x8000,flash的地址区间是0xA000-0xF000,A函数要调用B函数,则A函数调用B函数的那段汇编指令中包含的是B函数头的存储地址,A函数和B函数都在flash中有存储 1.1.2 情况1:B函数是配置为在RAM中运行, 阅读详情

相关推荐

为什么需要知识图谱?什么是知识图谱?——KG的前世今生

我的知乎专栏,对知识图谱感兴趣的朋友可以关注。标题的命名顺序可能让有的读者不太习惯。通常在介绍一个陌生事物的应用前,我们先给出其定义。之所以换个顺序,是为了不让读者一开始就接触比较冰冷生硬的概念刻板描述(后面我尽量用更具体、准确的例子来表达),另一方面也是为了通过现实生活中的例子自然的引入知识图谱的概念。希望通过这种方式加深读者的印象和理解。为了减轻读者理解的负担,我尽可能地避免引入过多的概念和技术

SimmerChan的专栏 8万+

Spring Bean生命周期源码篇

本文深入解析了Spring框架的核心原理,主要涵盖Bean生命周期、依赖注入、AOP实现和循环依赖处理机制。文章详细介绍了Bean的创建过程:从类加载、构造方法推断、依赖注入到初始化阶段,并重点分析了AOP的实现原理和事务管理机制。针对循环依赖问题,文章阐述了三级缓存(singletonObjects、earlySingletonObjects、singletonFactories)的解决方案。此外,还通过手写模拟代码展示了Spring底层工作机制,包括注解扫描、Bean创建、依赖注入和AOP代理等核心流程

qq_43649937的博客 2302

STM32F407单一定时器输出4路不同频率及占空比的PWM波

STM32F407单一定时器输出4路不同频率及占空比的PWM波

qq_43868701的博客 4918

SpringBean 生命周期源码解析

前言 Spring 作为当前 Java 最流行、最强大的轻量级框架,受到了程序员的青睐。准确的了解 Spring Bean 的生命周期是非常必要的,Spring Bean 的生命周期是 Spring 面试热点问题,想要答好并不容易!本文将从源码的角度入手,帮助小伙伴彻底掌握 Spring Bean 的生命周期。 而 Spring Bean 的生命周期只有 4 个阶段: 主要逻辑都在 doCreateBean 方法(AbstractAutowireCapableBeanFactory类中,逻辑很清晰,就是顺

养歌的博客 1491

STM32 SAI接口TDM模式实战:8通道音频采集系统搭建全流程(附DMA配置代码)

本文详细介绍了基于STM32 SAI接口TDM模式搭建8通道音频采集系统的全流程。内容涵盖硬件连接设计、CubeMX时钟树与SAI外设的详细配置,并重点解析了TDM模式的核心代码实现与DMA双缓冲机制,提供了完整的配置代码和常见时序问题排查指南,助力开发者高效实现多通道音频传输与处理。

weixin_29192211的博客 504

电子电器架构 --- OEM企标中规定ECU启动时间的目的

电子电器架构 --- OEM企标中规定ECU启动时间的目的

Soly_kun的博客 223

spring源码篇(三)bean的生命周期

人人都说spring是bean容器,也正体现了Bean的生命周期在spring中是至关重要的存在。我用思维导图把上面的流程捋了一遍。深色的就是上面的各个步骤,偏绿色,和绿色的是后置处理器的部分,一共6次调用,就是说我们有6次机会修改bean,还每一算上填充属性里的后置处理器。深蓝色和蓝绿色的是上面的生命周期阶段;绿色字体和蓝绿色的是后置处理器处理的调用;蓝色字体的是可以自定义实现的bean初始化的地方;那么还是围绕问题回顾一下为什么要有beanDefinition。

用针戳左手中指指头的博客 1307

【国产MCU系列】-GD32F4开发环境搭建(基于Embedded Builder)

GD32F4系列MCU采用Arm® Cortex®-M4内核,处理器主频高达240MHz,可支持算法复杂度更高的嵌入式应用,具备更快速的实时处理能力,并拥有业界领先的大容量存储优势。

视觉与物联智能 3078

【Spring】Spring之Bean生命周期源码解析

Spring之Bean生命周期源码解析

持续学习,坚持原创,分享技术笔记及经验。 804

MAC-电脑中的user文件夹在哪?

MAC-电脑中的user文件夹在哪?

兴趣是最好的老师 1万+

SAP-PLM传输MBOM传输至SAP

BOM 项目文本 (行 2)PLM创建及修改BOM接口。PLM 创建BOM接口抬头。BOM 项目文本(行1)PLM 创建BOM接口抬头。PLM BOM 错误消息。PLM BOM接口组件。组件数量 (BTCI)

qq_32198063的博客 431

spring bean生命周期详解,源码分析

目录如何获取beanClassPathXmlApplicationContext方法refresh源码分析finishBeanFactoryInitialization(beanFactory):spring bean的完整生命周期进阶版spring bean的完整生命周期 如何获取bean 首先,我们在代码中是怎样获取bean的,方式有以下几种,但不局限于这两种: @Test public void run1(){ //加载配置文件 ApplicationCont

李晨璐的博客 3575

Ubuntu22.04安装ros(一键搞定)

然后发现可以一键安装,话不多说,直接终端输入如下指令。回车之后系统会自动安装ros。

m0_47313541的博客 7413

Spring bean的生命周期,对比源码详解

为了更加熟悉spring的总体流程,看了spring的源码。 看了很多网上的资料写的spring的bean的生命周期,但是感觉和看到的源码有部分出入,这里再总结下。 正文: spring获取bean的时候有两种方式: BeanFactory bf = new XmlBeanFactory(new ClassPathResource("appli...

Jeff的专栏 5505

廖雪峰Python教程[完整版]

廖雪峰的python教程整理的,已经排好版了,而且还是完整的,适合小白

复分析 阿尔福斯(Ahlfors) 第三版答案 英文

答案分为十章,有部分习题没有答案,全英文复分析阿尔福斯(Ahlfors) 第三版答案

Spring Bean生命周期——从源码角度详解Spring Bean的生命周期(下)

书接上文Spring Bean生命周期——从源码角度详解Spring Bean的生命周期(上)postProcessBeforeInstantiation()在bean实例化前回调,返回实例则不对bean实例化,返回null则进行spring bean实例化(doCreateBean);postProcessAfterInstantiation()在bean实例化后在填充bean属性之前回调,返回true则进行下一步的属性填充,返回false则不进行属性填充;

秃了也弱了 1497

win10 跳过U8环境检测的IE WebControls.rar

win10 安装u8的时候 提示IE WebControls 不通过,这个工具可以欺骗u8的检查。 跳过U8环境检测的IE WebControls。提示导入失败后,重新检测通过。

Spring源码——Bean完整的生命周期详解

一、refresh方法二、实例化——createBeanInstance()1、回调方法实例化2、工厂方法实例化3、缓存实例化4、构造方法实例化1)获取适合的构造函数2)有参构造3)无参构造5、实例化前后1)postProcessBeforeInstantiation()2)postProcessAfterInstantiation()3)postProcessPropertyValues()三、属性赋值——populateBean()四、初始化——initializeBean()1、invokeAware

qq_25046827的博客 877

假人有限元模型

假人模型,车辆碰撞假人有限元模型,适合做乘员安全的研究者利用

Spring Bean的生命周期源码详解 - 【Spring底层原理】

一、源码分析 先分析源码,再来总结,从启动类开始,只会截取部分重要代码,但方法调用不会断 先来看看bean生命周期源码的脑图,可以跟着这个脑图来分析源码 源码分析:从AnnotationConfigApplicationContext开始 public AnnotationConfigApplicationContext(Class<?>... componentClasses) { this(); // 将beanDefinition对象存储到beanDefini

ONESTARの博客 798

Spring Bean生命周期——从源码角度详解Spring Bean的生命周期(上)

spring系列-注解驱动原理及源码-bean生命周期深入浅出弄明白Spring的BeanDefinition,Spring-Beans部分源码分析本文在此做更深入得讨论和研究,将源码吃透!总而言之,Spring BeanDefinition合并阶段,就是在RootBeanDefinition的基础上,添加或者修改成子类的属性。

秃了也弱了 1286

【Spring】Bean的作用域与Bean的生命周期详解【附源码】

Bean从创建到销毁称为Bean的生命周期,大体上Bean的生命周期共有七步: (1)通过无参构造器创建bean实例 (2)调用属性setter方法为bean的属性设置值 (3)把bean实例传递bean后置处理器的方法postProcessBeforeInitialization (4)调用bean的初始化的方法(需要配置初始化的方法) (5)把bean实例传递bean后置处理器的方法postProcessAfterInitialization (6)获取使用已经创建的bean (7)当容器关闭时候,调用

weixin_46081857的博客 641

Spring Bean的生命周期各阶段详解附源码

spring bean的生命周期过程解析附源码,搞清各阶段所做的事情

SeeYouAgain的博客 416

Spring Bean的生命周期源码详解 - 【Spring底层原理】

单例池就是已经实例化好的对象我就放进去,我要用的时候直接从池子里面拿,不用再实例化一遍,这时候从单例池中get,所有的对象第一次实例化都要过来这里,第一次单例池里面肯定是没有的。其实这里有个比较重要的知识点,解决循环依赖的三级缓存,这里提一下,后面会专门出文章讲解循环依赖,有疑惑的伙伴可以跳过,只要知道可以用来创建bean就可以了。在doCreateBean这个方法中,完成了bean的实例化,属性注入和初始化,bean的实例化就是在createBeanInstance方法执行的。

2401_84166896的博客 1150

Spring Bean 生命周期详解——从出生到销毁,结合源码全程追踪

出生 → 成长 → 工作 → 退休。Bean 的一生:出生(实例化)→ 打疫苗/上学(属性填充 + 初始化)→ 上班干活(使用)→ 退休(销毁)Spring 官方文档对 Bean 生命周期的描述:Spring Framework 官方文档 - Lifecycle Callbacks翻译:Spring IoC 容器管理 Bean 的生命周期。容器根据配置元数据来创建和管理 Bean。Spring 提供了多种机制让你介入 Bean 的生命周期管理。通俗理解:Bean 的生命周期就是。

cjejwe的博客 1026

Spring 源码 | bean的生命周期(图文详解)

下面先用一张图描述下 bean 装载到 Spring 应用上下文中的一个典型的生命周期过程: 下面对上面的图进行详细解读: 1、首先容器启动后,会对scope为singleton且非懒加载的bean进行实例化; 2、按照Bean定义信息配置信息,注入所有的属性 (依赖注入"DI"); 3、如果 bean 实现了 BeanNameAware 接口,Spring 会回调该接口的 setBeanName () 方法,传递该Bean的id,此时该Bean就获得了自己在配置文件中的id; 4、如果 bean 实现了

Awwwze的博客 628

Spring IOC源码解析:Spring Bean生命周期详解(一)

介绍 参考博客 [1]

小识的博客 845

Spring源码解析-Bean生命周期详解

1.调用构造器构造对象: 默认使用无参构造方法,若声明有参构造方法,则自动注入参数,调用有参构造方法(如果有多个有参构造方法,则会抛出无默认构造方法异常),如果参数在spring容器中无bean对象,即无法注入,则会抛出异常。若有多个有参构造方法,可使用@Autowired注解来标记默认使用的构造方法 2.注入属性: spring会先扫描切入点(即被autowire注解标注的属性),然后跟字段类型,扫描容器中所有的bean,找出符合该类型的所有bean,然后根据bean...

weixin_55605815的博客 224

spring5源码阅读(六)Spring Bean的生命周期详解+Demo

文章目录1 生命周期整体流程1.1 实例化1.2 初始化1.3 销毁2 Demo演示 本文分析下bean的生命周期,spring bean从创建到初始化,在到销毁的过程。其中初始化的过程中,spring又为我们留了几个接口,方便我们实现一些特殊的效果。 1 生命周期整体流程 bean的生命周期总结为3大步骤: 实例化 初始化 销毁 1.1 实例化 前面文章中spring5源码阅读(三)的最后...

雨剑的博客 671
上一篇: Spring 三级缓存解决循环依赖源码分析
下一篇: Spring MVC源码详解
ludkjava
博客等级 码龄11年 173粉丝 32原创
评论
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符
 
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

个

红包个数最小为10个

元

红包金额最低5元

当前余额3.43元 前往充值 >
需支付:10.00元
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付元
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值