Spring 源码阅读 BeanFactory(三) 对象的初始化 singleton 草稿

Spring之AOP代理对象的产生(一) 准备 接口 public interface UserService { String query(); } 接口的实现 @Service public class UserServiceImpl implements UserService { @Override public String query() { System.out.println("------------ yz ------------"); return "yz"; 阅读详情

前言

前几篇文章已经说明Spring对BeanDefinition的解析与维护,在beans->bean标签定义下的bean 默认会通过 org.springframework.beans.factory.support.DefaultListableBeanFactory.registerBeanDefinition(String beanName, BeanDefinition beanDefinition)方法注册到BeanFactory中,我们到目前为止,在BeanDefinition解析的链条中并没有发现有实例化Bean的行为,毕竟我们使用Bean时可以简单到使用getBean方法就能拿到一个实例化对象,那么Bean是何时被初始化的?带着这个疑问继续分析Spring源码,找到Bean初始化的真相。

源码

按照前几文的逻辑链,beanDefinition是在刷新ApplicationContext时注册进来的,那么回到org.springframework.context.support.AbstractApplicationContext.refresh() 方法

*下边有两个接口,如果不清楚作用和意义的话,可能影响阅读,可以看道某友的博文《Spring的BeanFactoryPostProcessor和BeanPostProcessor》 写的不错

org.springframework.beans.factory.config.BeanFactoryPostProcessor
org.springframework.beans.factory.config.BeanPostProcessor

借用道友的图,和部分文字(话说我之前怎么想不到这么说明问题呢……)
这里写图片描述
“而BeanPostProcessor的执行,取决于配置文件中bean的定义,如果定义的bean是singleton并且不是抽象类,也不延迟初始化,则BeanPostProcessor是在第11步中执行;而对于prototype的bean,BeanPostProcessor是在程序getBean的时候执行的。”

singleton 非延迟加载(non-lazy-init)

按文字说明来到第11步finishBeanFactoryInitialization(beanFactory)
其源码如下,其他都不重要,主要看beanFactory.preInstantiateSingletons(); 这一行

/**
     * Finish the initialization of this context's bean factory,
     * initializing all remaining singleton beans.
     */
    protected void finishBeanFactoryInitialization(ConfigurableListableBeanFactory beanFactory) {
        // Initialize conversion service for this context.
        if (beanFactory.containsBean(CONVERSION_SERVICE_BEAN_NAME) &&
                beanFactory.isTypeMatch(CONVERSION_SERVICE_BEAN_NAME, ConversionService.class)) {
            beanFactory.setConversionService(
                    beanFactory.getBean(CONVERSION_SERVICE_BEAN_NAME, ConversionService.class));
        }

        // Register a default embedded value resolver if no bean post-processor
        // (such as a PropertyPlaceholderConfigurer bean) registered any before:
        // at this point, primarily for resolution in annotation attribute values.
        if (!beanFactory.hasEmbeddedValueResolver()) {
            beanFactory.addEmbeddedValueResolver(new StringValueResolver() {
                @Override
                public String resolveStringValue(String strVal) {
                    return getEnvironment().resolvePlaceholders(strVal);
                }
            });
        }

        // Initialize LoadTimeWeaverAware beans early to allow for registering their transformers early.
        String[] weaverAwareNames = beanFactory.getBeanNamesForType(LoadTimeWeaverAware.class, false, false);
        for (String weaverAwareName : weaverAwareNames) {
            getBean(weaverAwareName);
        }

        // Stop using the temporary ClassLoader for type matching.
        beanFactory.setTempClassLoader(null);

        // Allow for caching all bean definition metadata, not expecting further changes.
        beanFactory.freezeConfiguration();

        // Instantiate all remaining (non-lazy-init) singletons.
        // *重要 看这里
        beanFactory.preInstantiateSingletons();
    }

最后一行在做了各种准备之后,调用beanFactory.preInstantiateSingletons();方法“Instantiate all remaining (non-lazy-init) singletons.”我们谷歌一下,其人话为“实例化所有剩下的(非懒惰init)单例。”这就很好理解了,所有非延迟加载的单例bean都在这个方法中实例化,那么是如何实例化的呢?ctrl+alt+b 试一下。正好直接看到这个方法实现只有一个,就是那位老朋友org.springframework.beans.factory.support.DefaultListableBeanFactory这个类,下面分析一下这个类

@Override
    public void preInstantiateSingletons() throws BeansException {
        if (this.logger.isDebugEnabled()) { //日志(这是一种好的日志处理方式,当没有开启debug级别时,就会省下一次字符串拼接),spring源码里到处都是这样的处理,可以学习。
            this.logger.debug("Pre-instantiating singletons in " + this);
        }

        // Iterate over a copy to allow for init methods which in turn register new bean definitions.
        // While this may not be part of the regular factory bootstrap, it does otherwise work fine.
        //拷贝一个新的list ,this.beanDefinitionNames 干嘛的,上文大概已有说明,可以结合《Spring 源码阅读 BeanFactory(二) 之registerBeanDefinition方法》一块看
        List<String> beanNames = new ArrayList<String>(this.beanDefinitionNames);

        // Trigger initialization of all non-lazy singleton beans...
        for (String beanName : beanNames) { //遍历beanName
            //这里先解释一下getMergedLocalBeanDefinition方法的含义,因为这个方法会常常看到。Bean定义公共的抽象类是AbstractBeanDefinition,普通的Bean在Spring加载Bean定义的时候,实例化出来的是GenericBeanDefinition,而Spring上下文包括实例化所有Bean用的AbstractBeanDefinition是RootBeanDefinition,这时候就使用getMergedLocalBeanDefinition方法做了一次转化,将非RootBeanDefinition转换为RootBeanDefinition以供后续操作。
            RootBeanDefinition bd = getMergedLocalBeanDefinition(beanName);
            if (!bd.isAbstract() && bd.isSingleton() && !bd.isLazyInit()) {//非抽象的,单例的,非懒加载的
                if (isFactoryBean(beanName)) { //Spring中有两种类型的Bean,一种是普通Bean,另一种是工厂Bean,即FactoryBean, 工厂Bean 再起炉灶
                    final FactoryBean<?> factory = (FactoryBean<?>) getBean(FACTORY_BEAN_PREFIX + beanName);
                    boolean isEagerInit;
                    if (System.getSecurityManager() != null && factory instanceof SmartFactoryBean) {
                        isEagerInit = AccessController.doPrivileged(new PrivilegedAction<Boolean>() {
                            @Override
                            public Boolean run() {
                                return ((SmartFactoryBean<?>) factory).isEagerInit();
                            }
                        }, getAccessControlContext());
                    }
                    else {
                        isEagerInit = (factory instanceof SmartFactoryBean &&
                                ((SmartFactoryBean<?>) factory).isEagerInit());
                    }
                    if (isEagerInit) {
                        getBean(beanName);
                    }
                }
                else { //非工厂Bean 调用该方法
                    getBean(beanName);
                }
            }
        }

        // Trigger post-initialization callback for all applicable beans...
        // 暂时不重要,MARK
        for (String beanName : beanNames) {
            Object singletonInstance = getSingleton(beanName);
            if (singletonInstance instanceof SmartInitializingSingleton) {
                final SmartInitializingSingleton smartSingleton = (SmartInitializingSingleton) singletonInstance;
                if (System.getSecurityManager() != null) {
                    AccessController.doPrivileged(new PrivilegedAction<Object>() {
                        @Override
                        public Object run() {
                            smartSingleton.afterSingletonsInstantiated();
                            return null;
                        }
                    }, getAccessControlContext());
                }
                else {
                    //MARK
                    smartSingleton.afterSingletonsInstantiated();
                }
            }
        }
    }

这里主要的就是getBean(beanName)了。

    @Override
    public Object getBean(String name) throws BeansException {
        return doGetBean(name, null, null, false);
    }

getBean方法内部调用了一个doGetBean方法,其源码如下,简单机翻一下其文档注释Return an instance, which may be shared or independent, of the specified bean. “返回指定bean的一个可能是共享的或独立的实例。”

/**
     * Return an instance, which may be shared or independent, of the specified bean.
     * @param name the name of the bean to retrieve
     * @param requiredType the required type of the bean to retrieve
     * @param args arguments to use when creating a bean instance using explicit arguments
     * (only applied when creating a new instance as opposed to retrieving an existing one)
     * @param typeCheckOnly whether the instance is obtained for a type check,
     * not for actual use
     * @return an instance of the bean
     * @throws BeansException if the bean could not be created
     */
    @SuppressWarnings("unchecked")
    protected <T> T doGetBean(
            final String name, final Class<T> requiredType, final Object[] args, boolean typeCheckOnly)
            throws BeansException {
        //是对你传入的bean的name的转换,代码内部用到了BeanFactoryUtils.transformedBeanName(name)方法,该方法主要是去掉以String FACTORY_BEAN_PREFIX = "&";开头的bean的name,截取&后面的部分,最后会查看private final Map<String, String> aliasMap = new ConcurrentHashMap<String, String>(16);别名map中是否已经存在这个bean name 存在则沿用以前的bean name
        final String beanName = transformedBeanName(name);
        Object bean;

        // Eagerly check singleton cache for manually registered singletons.
        // 检查该beanName缓存中是否已经注册过,这里自己测试了下,对同一个BeanName,第一次执行doGetBean方法时,该方法返回null(部分通过registerSingleton(@NotNull String beanName,Object singletonObject))先行注册的工厂bean等其他Bean除外,该方法会检查Map singletonObjects(Cache of singleton objects: bean name --> bean instance)是否存在对应的bean实例,如果存在则返回对应的 bean instance
        Object sharedInstance = getSingleton(beanName);
        if (sharedInstance != null && args == null) {//如果上一步获得的sharedInstance 不为null
            if (logger.isDebugEnabled()) {
                if (isSingletonCurrentlyInCreation(beanName)) {
                    logger.debug("Returning eagerly cached instance of singleton bean '" + beanName +
                            "' that is not fully initialized yet - a consequence of a circular reference");
                }
                else {
                    logger.debug("Returning cached instance of singleton bean '" + beanName + "'");
                }
            }
            //
            bean = getObjectForBeanInstance(sharedInstance, name, beanName, null);
        }

        else {
            // Fail if we're already creating this bean instance:
            // We're assumably within a circular reference.
            // 如果已经正在创建bean实例,则抛出一个异常
            if (isPrototypeCurrentlyInCreation(beanName)) {
                throw new BeanCurrentlyInCreationException(beanName);
            }

            // Check if bean definition exists in this factory.
            // 通常情况下 parentBeanFactory 为null
            BeanFactory parentBeanFactory = getParentBeanFactory();
            if (parentBeanFactory != null && !containsBeanDefinition(beanName)) {//如果找到双亲工厂,并且不存在这个bean定义,
                // Not found -> check parent.
                String nameToLookup = originalBeanName(name);
                if (args != null) {
                    // Delegation to parent with explicit args.
                    return (T) parentBeanFactory.getBean(nameToLookup, args);
                }
                else {
                    // No args -> delegate to standard getBean method.
                    return parentBeanFactory.getBean(nameToLookup, requiredType);
                }
            }

            if (!typeCheckOnly) {
                markBeanAsCreated(beanName);
            }

            try {
                final RootBeanDefinition mbd = getMergedLocalBeanDefinition(beanName);
                checkMergedBeanDefinition(mbd, beanName, args);
                // 拿到bean的定义
                // Guarantee initialization of beans that the current bean depends on.
                String[] dependsOn = mbd.getDependsOn(); //bean的第一次创建,不管业务上是否对其他bean存在依赖,但是这里拿到的是null,我的测试类存在两个依赖。这里拿到的是null
                if (dependsOn != null) { 
                    for (String dep : dependsOn) {
                        if (isDependent(beanName, dep)) {
                            throw new BeanCreationException(mbd.getResourceDescription(), beanName,
                                    "Circular depends-on relationship between '" + beanName + "' and '" + dep + "'");
                        }
                        registerDependentBean(dep, beanName);
                        getBean(dep);
                    }
                }

                // Create bean instance.
                if (mbd.isSingleton()) {
                    //getSingleton 内部其实是将通过createBean 创建的bean实例,通过getObject方法获得,然后将其加入到缓存中。
                    sharedInstance = getSingleton(beanName, new ObjectFactory<Object>() {
                        @Override
                        public Object getObject() throws BeansException {
                            try {
                                //MARK :主要逻辑
                                return createBean(beanName, mbd, args);
                            }
                            catch (BeansException ex) {
                                // Explicitly remove instance from singleton cache: It might have been put there
                                // eagerly by the creation process, to allow for circular reference resolution.
                                // Also remove any beans that received a temporary reference to the bean.
                                destroySingleton(beanName);
                                throw ex;
                            }
                        }
                    });

                    bean = getObjectForBeanInstance(sharedInstance, name, beanName, mbd);
                }

                else if (mbd.isPrototype()) { //多例的处理,不在本文的讨论范围
                    // It's a prototype -> create a new instance.
                    Object prototypeInstance = null;
                    try {
                        beforePrototypeCreation(beanName);
                        prototypeInstance = createBean(beanName, mbd, args);
                    }
                    finally {
                        afterPrototypeCreation(beanName);
                    }
                    bean = getObjectForBeanInstance(prototypeInstance, name, beanName, mbd);
                }

                else {
                    String scopeName = mbd.getScope();
                    final Scope scope = this.scopes.get(scopeName);
                    if (scope == null) {
                        throw new IllegalStateException("No Scope registered for scope name '" + scopeName + "'");
                    }
                    try {
                        Object scopedInstance = scope.get(beanName, new ObjectFactory<Object>() {
                            @Override
                            public Object getObject() throws BeansException {
                                beforePrototypeCreation(beanName);
                                try {
                                    return createBean(beanName, mbd, args);
                                }
                                finally {
                                    afterPrototypeCreation(beanName);
                                }
                            }
                        });
                        bean = getObjectForBeanInstance(scopedInstance, name, beanName, mbd);
                    }
                    catch (IllegalStateException ex) {
                        throw new BeanCreationException(beanName,
                                "Scope '" + scopeName + "' is not active for the current thread; consider " +
                                "defining a scoped proxy for this bean if you intend to refer to it from a singleton",
                                ex);
                    }
                }
            }
            catch (BeansException ex) {
                cleanupAfterBeanCreationFailure(beanName);
                throw ex;
            }
        }

        // Check if required type matches the type of the actual bean instance.
        if (requiredType != null && bean != null && !requiredType.isAssignableFrom(bean.getClass())) {
            try {
                return getTypeConverter().convertIfNecessary(bean, requiredType);
            }
            catch (TypeMismatchException ex) {
                if (logger.isDebugEnabled()) {
                    logger.debug("Failed to convert bean '" + name + "' to required type '" +
                            ClassUtils.getQualifiedName(requiredType) + "'", ex);
                }
                throw new BeanNotOfRequiredTypeException(name, requiredType, bean.getClass());
            }
        }
        return (T) bean;
    }

createBean方法

上一节说,创建实例时是通过creanBean方法,其代码如下

/**
     * Central method of this class: creates a bean instance,
     * populates the bean instance, applies post-processors, etc.
     * @see #doCreateBean
     */
    @Override
    protected Object createBean(String beanName, RootBeanDefinition mbd, Object[] args) throws BeanCreationException {
        if (logger.isDebugEnabled()) {
            logger.debug("Creating instance of bean '" + beanName + "'");
        }
        RootBeanDefinition mbdToUse = mbd;

        // Make sure bean class is actually resolved at this point, and
        // clone the bean definition in case of a dynamically resolved Class
        // which cannot be stored in the shared merged bean definition.
        // 获得bean定义的class对象
        Class<?> resolvedClass = resolveBeanClass(mbd, beanName);
        if (resolvedClass != null && !mbd.hasBeanClass() && mbd.getBeanClassName() != null) {
            mbdToUse = new RootBeanDefinition(mbd);
            mbdToUse.setBeanClass(resolvedClass);
        }

        // Prepare method overrides.
        try {
            mbdToUse.prepareMethodOverrides();
        }
        catch (BeanDefinitionValidationException ex) {
            throw new BeanDefinitionStoreException(mbdToUse.getResourceDescription(),
                    beanName, "Validation of method overrides failed", ex);
        }

        try {
            // Give BeanPostProcessors a chance to return a proxy instead of the target bean instance.
            // 判断哪些bean使用Aop代理生成代理对象,哪些bean使用构造方法反射生成实例。使用构造方法反射生成实例的方式,该方法会返回null
            Object bean = resolveBeforeInstantiation(beanName, mbdToUse);
            if (bean != null) {
                return bean;
            }
        }
        catch (Throwable ex) {
            throw new BeanCreationException(mbdToUse.getResourceDescription(), beanName,
                    "BeanPostProcessor before instantiation of bean failed", ex);
        }
        //创建对象
        Object beanInstance = doCreateBean(beanName, mbdToUse, args);
        if (logger.isDebugEnabled()) {
            logger.debug("Finished creating instance of bean '" + beanName + "'");
        }
        return beanInstance;
    }

doCreateBean方法根据传入的beanName和 beanDefination创建一个实例,并将其加入缓存

/**
     * Actually create the specified bean. Pre-creation processing has already happened
     * at this point, e.g. checking {@code postProcessBeforeInstantiation} callbacks.
     * <p>Differentiates between default bean instantiation, use of a
     * factory method, and autowiring a constructor.
     * @param beanName the name of the bean
     * @param mbd the merged bean definition for the bean
     * @param args explicit arguments to use for constructor or factory method invocation
     * @return a new instance of the bean
     * @throws BeanCreationException if the bean could not be created
     * @see #instantiateBean
     * @see #instantiateUsingFactoryMethod
     * @see #autowireConstructor
     */
    protected Object doCreateBean(final String beanName, final RootBeanDefinition mbd, final Object[] args)
            throws BeanCreationException {

        // Instantiate the bean.
        BeanWrapper instanceWrapper = null;
        if (mbd.isSingleton()) {
            instanceWrapper = this.factoryBeanInstanceCache.remove(beanName);
        }
        if (instanceWrapper == null) {
            instanceWrapper = createBeanInstance(beanName, mbd, args);
        }
        final Object bean = (instanceWrapper != null ? instanceWrapper.getWrappedInstance() : null);
        Class<?> beanType = (instanceWrapper != null ? instanceWrapper.getWrappedClass() : null);
        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.isDebugEnabled()) {
                logger.debug("Eagerly caching bean '" + beanName +
                        "' to allow for resolving potential circular references");
            }

            addSingletonFactory(beanName, new ObjectFactory<Object>() {
                @Override
                public Object getObject() throws BeansException {
                    return getEarlyBeanReference(beanName, mbd, bean);
                }
            });
        }

        // Initialize the bean instance.
        Object exposedObject = bean;
        try {
            populateBean(beanName, mbd, instanceWrapper);
            if (exposedObject != null) {
                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<String>(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 " +
                                "'getBeanNamesOfType' 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;
    }
钉钉Java面经及参考答案 TCP 三次握手建立连接的核心目标是双向确认双方发送、接收能力,同步通信序列号,协商初始窗口大小,防止历史过期连接报文干扰新连接。第一次握手,客户端主动向服务端发送 SYN 报文,携带客户端随机生成的初始序列号 ISN,客户端状态变更为 SYN_SENT,目的是告知服务端客户端具备发送数据的能力。第二次握手,服务端收到 SYN 报文后,回复 SYN+ACK 报文,其中 ACK 确认号为客户端 ISN+1,同时携带服务端自身随机初始序列号,服务端进入 SYN_RCVD 状态,代表服务端确认收到客户端报文,且自 阅读详情

相关推荐

Dify实战应用指南(上传需求稿生成测试用例)

摘要: Dify是一款开源大语言模型应用开发平台,通过低代码/无代码方式支持AI应用开发。平台提供五种核心应用类型,包括聊天助手、文本生成、Agent、ChatFlow和Workflow,适用于不同场景。本文以ChatFlow为例,演示如何上传需求稿自动生成测试用例。通过条件分支、文档提取器和LLM设置,实现从需求文档到测试用例的自动化转换,显著提升测试效率并降低人工误差。该方案适用于需要快速生成测试用例的软件开发场景,尤其适合非技术人员使用。

Linda的自动化测试之旅 2744

可能是最卷的Spring源码系列(十三):beanFactory.preInstantiateSingletons() 方法解析

preInstantiateSingletons方法也是spring中最重要的方法之一,bean的实例化、aop、生命周期的执行等重要的步骤都是在这里面执行。有了上篇循环依赖的基础,我们一定能把这个方法分析透彻。 finishBeanFactoryInitialization protected void finishBeanFactoryInitialization(ConfigurableListableBeanFactory beanFactory) { // Initialize convers

wanghao的博客 1169

STM32异常与中断过程详解

1. 异常与中断概念引入 异常主要是指来自CPU内部的意外事件,比如执行了未定义指令、算术溢出、除零运算等发生在CPU内部的意外事件,这些异常的发生,会引起CPU运行相应的异常处理程序;中断一般来自硬件(如片上外设、外部I/O输入等)发生的事件,当这些硬件产生中断信号时,CPU会暂停当前运行的程序,转而去处理相关硬件的中断服务程序。但无论是异常还是中断,都会引起程序执行偏离正常的流程,转而去执行异常/中断的处理函数。 下面对异常和中断的介绍,如果中断信号的产生原因来自CPU内部,则称之为异常;如果中断信号来

luobeihai的博客 1万+

beanfactory中单例bean的初始化过程(一)

Date 10.06 pm Point 完成beanfactory中单例bean的初始化 beanFactory.preInstantiateSingletons() 拿到所有的bean定义信息(在 beanDefinitionNames中,遍历list 获取到bean的定义信息 如果这个bean不是抽象,是单例,不是懒加载的 判断这个bean是否factorybean(判断这个...

qq_36090711的博客 499

ADS与Cadence中Verilog-A文件的编译与调用实战指南

本文详细介绍了在ADS与Cadence平台中Verilog-A文件的编译与调用实战指南,涵盖开发环境配置、模型创建与编译、仿真设置技巧以及跨平台协作与调试等内容。通过具体案例和优化策略,帮助工程师高效完成混合信号仿真设计,提升电路建模与验证效率。

weixin_29196315的博客 498

使用Xpath语法爬取豆瓣读书Top250

使用Xpath语法爬取豆瓣读书Top250 使用的软件是Spyder 网页地址:https://book.douban.com/top250?start=0 直接上代码: # -*- coding: utf-8 -*- """ Created on Thu Apr 30 18:35:17 2020 @author: ASUS """ import requests import csv fr...

weixin_43987253的博客 2081

(四)BeanFactory初始化Singleton的实现细节

1.介绍 查看ApplicationContext的启动以及初始化部分的代码时,发现最终实现对象创建以及所有非懒加载的单例对象整体初始化,都是通过DefaultListableBeanFacotry来实现的 其中对象创建是通过beanFactory.getBean(xxx)来实现,而整体初始化是通过beanFactory.preInstantiateSingletons();来实现, 下面针对这...

流连是谁的博客 4766

PCL ——LevenbergMarquardt非线性最小二乘法拟合圆柱(C++详细过程版)

使用C++详细过程版实现的LevenbergMarquardt非线性最小二乘法拟合圆柱

点云侠的博客 607

Spring注解驱动开发第46讲——Spring IOC容器创建源码解析(六)之初始化所有剩下的单实例bean(上)

写在前面 在前面几讲中,我们已经对IOC容器创建过程中的大部分方法进行过研究,其中比较核心的方法就是如下两个: invokeBeanFactoryPostProcessors方法:该方法在《Spring注解驱动开发第42讲——Spring容器创建源码解析(二)之执行BeanFactoryPostProcessor》这一讲中已经详细讲过了,要是还有不清楚的同学,可以查阅这篇文章哟! registerBeanPostProcessors方法:该方法在《Spring注解驱动开发第43讲——Spring容器创建源

李阿昀的博客 1866

手把手教你学PCIE--基本概念:PCIe 初始化流程概述

硬件上电复位:系统上电时,所有 PCIe 设备都会进行复位。链路训练(Link Training):主机和设备之间通过链路训练状态机(LTSSM)协商链路参数(如速度和宽度)。配置空间访问:主机通过配置空间读写来发现和配置设备。资源分配:主机为设备分配内存映射 I/O 区域(BARs)、中断向量等资源。驱动程序加载和高级配置:操作系统加载设备驱动程序,并进行更高级的配置和状态监控。硬件上电复位:确保所有设备处于已知的良好状态。链路训练:主机和设备通过 LTSSM 协商链路速度和宽度。

MHD0815的博客 1375

提升JVM性能:CMS垃圾回收器的优化分析与案例研究

本文介绍了CMS(Concurrent Mark-Sweep)垃圾回收器的工作原理、优缺点及常见问题,并通过具体案例分析了其优化策略。重点探讨了CMS的各个阶段,包括标记、并发清理和重标记,分析了可能导致性能瓶颈的因素如停顿时间过长和内存碎片化。文章还分享了调整垃圾回收参数、结合其他垃圾回收器以及内存优化等方法,帮助提高CMS的回收效率和性能。最后,文章展望了随着JVM发展,结合新一代垃圾回收器优化的趋势,助力Java应用在高并发环境下的性能提升。

曾经“等你生日那天”都遥远得像未来,如今却可欢愉的挥手说“下个十年见” 175万+

【Spring源码阅读】 preInstantiateSingletons方法分析,单例Bean获取/实例化流程

在初始化ClassPathXmlApplicatonContext过程中,核心初始化逻辑在AbstractApplicationContext的refresh函数中: public void refresh() throws BeansException, IllegalStateException { synchronized (this.startupShutdownMonitor) { ...

总结沉淀 4712

android 蓝牙通讯demo

android 下蓝牙通讯demo,实现了发现蓝牙,使能蓝牙,通过蓝牙发送消息。

详解Spring启动实例化非懒加载的单例Bean

一、实例化所有非懒加载的单例 不论是基于注解的Spring容器,还是基于xml的Spring容器,在启动的过程中,都会调用AbstractApplicationContext的refresh(),在该方法中,通过调用finishBeanFactoryInitialization(beanFactory)来实例化所有非懒加载的单例Bean protected void finishBeanFactoryInitialization(ConfigurableListableBeanFactory beanFac

sermonlizhi的博客 837

华为的C语言编程规范.pdf

华为技术有限公司内部技术规范。本规范制定了编写C语言程序的基本原则、规则和建议。从代码的清晰、简洁、可测试、安全、程序效率、可移植各个方面对C语言编程作出了具体指导。

jre9下载 jdk9

(Java SE Runtime Environment 9.0) 9.0u175 官方最新版 【x86|x64】

spring启动一直Pre-instantiating singletons原因及解决方案

今天帮同事排查一个问题,他开发完并未经过本地测试,便提交代码,发布到预生产测试环境,启动 server 过程中一直卡在 Pre-instantiating singletons 无法成功启动项目,我在本地调试后发现并成功定位此问题。 项目环境: spring 3.x mybatis 3.x logback 问题: 应用服务器(tomcat、jetty、jboss等)启动项目一直卡在 Pre-ins...

朝花夕拾 3868

jdk-8u144-linux-x64.tar.gz.

该资源为搭建Linux系统Java环境用,资源的后缀为tar.gz格式的压缩包

【五】Spring源码分析之实例化Bean----DefaultListableBeanFactory的preInstantiateSingletons方法

一、简介 该方法最主要做的事是:把BeanDefinition注册表中的所有单例、非懒加载的bean全部实例化 该方法的入口: 二、源码分析 DefaultListableBeanFactory类preInstantiateSingletons方法 public void preInstantiateSingletons() throws BeansException { if...

Sid小杰的博客 2659

Spring源码解析四之创建Bean(解决循环依赖)

首先,循环依赖是啥,用白话说,最简单的案例就是A中有B,而B中又有A,这样一个例子并不能说明什么,但是Spring容器创建Bean是有顺序的。 假设有A、B两类 public class A { B b; public B getB() { return b; } public void setB(B b) { this.b = b; } } public class B { A a; public A g

小陈陈陈陈生 582

spring源码学习之代理类创建过程

上篇中讲到spring将所有的标签解析完成并封装成为RootBeanDefinition之后,并将RootBeanDefinition存储在BeanFactory工厂类的Map<String, BeanDefinition> beanDefinitionMap变量中,这篇接着分析spring使用aop面向切面编程,来实现对事物的控制,spring容器是如何创建目标类的代理类。 Bea...

lihuayong的专栏 2389

深入理解Spring源码之IOC 扩展原理BeanFactoryPostProcessor和事件监听ApplicationListener

2.BeanFactoryPostProcessor 一个好的框架必备的特性至少得有开闭原则,可扩展性BeanFactoryPostProcessor也是Spring可扩展性的一个体现,我们读一下这个接口的源码 public interface BeanFactoryPostProcessor { /** * Modify the application context'...

数据与算法架构提升之路专栏 832

Spring注解驱动开发——Bean的创建

一、finishBeanFactoryInitialization(beanFactory);初始化所有剩下的单实例bean 1、beanFactory.preInstantiateSingletons(); 1)、获取容器中的所有Bean,依次进行初始化和创建对象 2)、获取Bean的定义信息:RootBeanDefinition 判断当Bean是单实例的,不是抽象的,不是懒加载的时候...

如不來的博客 413

spring系列14:实例化Bean

前言 registerBeanPostProcessors之后,Spring要开始准备实例化Bean。不过在这之前,Spring初始化了非常多的内部组件。 // 国际化消息组件 initMessageSource(); // Initialize event multicaster for this context. // 初始化事件监听多路广播器 initApplicationEventMulticaster(); // Initialize other special beans in...

chuixue24的博客 316

Spring IOC源码笔记(三)

目录 一、finishBeanFactoryInitialization(beanFactory):初始化所有剩下的非懒加载的单例Bean 二、finishRefresh():完成上下文的刷新工作 三、总结 一、finishBeanFactoryInitialization(beanFactory):初始化所有剩下的非懒加载的单例Bean finishBeanFactoryInitialization(beanFactory)主要完成所有剩下的非懒加载的单例bean的初始化,这个方法非常重要,可以

weixiaohuai的博客 1740

spring 源码核心方法之 finishBeanFactoryInitialization(beanFactory)解析(六)

今天我们讲解spring 启动过程中最核心方法,我们计划分多篇讲解,今天解析该方法的主干核心,后几篇我们解析该方法相关的分支方法(为啥啊?因为这个方法太重要了!),废话少说,看源码! 1、来到 AbstractApplicationContext extends DefaultResourceLoader implements ConfigurableApplicationContext ............

nandao158的博客 600

【Spring源码】- 03 Spring IoC容器启动之Bean创建流程

上篇已经分析完refresh()中大部分方法,也已经把Bean解析成BeanDefinition注册到IoC容器中,refresh还剩下一个非常重要的方法,就是下面将要分析的:finis...

god_86的专栏 366

preInstantiateSingletons()方法——(三)

Spring源码之preInstantiateSingletons()方法

qq_46144673的博客 429

Spring - SmartInitializingSingleton扩展接口

Spring Boot - 扩展接口一览 触发时机 只有一个方法,其作用是是 在spring容器管理的所有单例对象(非懒加载对象)初始化完成之后调用的回调接口。其触发时机为之后。可以扩展此接口在对所有单例对象初始化完毕后,做一些后置的业务处理 在Spring容器启动时,会调用方法; 重点看 继续 继续 扩展示例

小工匠 3万+
上一篇: Redis Cluster处理MULTI/EXEC事务以及Multiple主键命令时的限制
下一篇: Dubbo 对配置文件的解析
weiythi
博客等级 码龄16年 23粉丝 48原创
评论
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符
 
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

个

红包个数最小为10个

元

红包金额最低5元

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

抵扣说明:

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

余额充值