• 理解Spring 容器、BeanFactory 以及 ApplicationContext


    一、spring 容器理解

    spring 容器可以理解为生产对象(Object)的地方,在这里容器不只是帮助我们创建对象那么简单,它负责了对象的整个生命周期-创建、装配、销毁。而这里对象的创建管理的控制器都交给

    了spring 容器,所以这是一种控制权的反转,称为IOC 容器,而这里 IOC 容器不只是 Spring 才有,很多框架也有此技术。

    二、BeanFactory 和 ApplicationContext 之间的关系

    • BeanFactory 和 ApplicationContext 是 Spring 的两大接口,而其中 ApplicationContext 是 BeanFactory 的子接口。它们都可以当作 Spring 的容器,Spring 容器是生成 Bean 实例的工厂,并

    管理容器中的Bean。 在基于 Spring 的 Java 应用中,所有的组件都被当成 Bean 处理,包括数据源,Hibernate 的 SessionFactory 、事务管理器等。

    • 生活中一般把生产产品的地方称为工厂,而这里 bean 对象的地方称为 BeanFactory,直译 Bean 工厂(com.springframework.beans.factory.BeanFactory),我们一般称 BeanFactory 为 Ioc 容器,而

    称 ApplicationContext 称为应用上下文。

    Spring 的核心是容器,而容器并非唯一的,框架本身就提供了很多容器的实现,大概分两种类型:

    • 一种不常用的 BeanFactory ,这是最简单的容器,只能提供基本的DI 功能
    • 一种就是继承了BeanFactory 后派生而来的 ApplicationContext(应用上下文),它能提供更多企业级的服务,例如解析配置文本信息等等,这也是 ApplicationContext 实例对象常见的应用场景

    三、BeanFactory 详情

    Spring 容器最基本的接口就是 BeanFactory , BeanFactory 负责配置、创建、管理Bean ,它有一个子接口 ApplicationContext ,也被称为 Spring 上下文,容器同时还管理着 Bean 和 Bean 之间的

    依赖关系。

    Spring Ioc容器的实现,从根源上是 BeanFactory,但真正的可以独立使用的 Ioc 容器还是 DefaultListableBeanFactory ,因此可以这么说,DefaultListableBeanFactory 是整个 Spring Ioc 的始祖。

     接口介绍

    BeanFactory 接口

    是Spring bean容器的根接口,提供获取bean,是否包含bean,是否单例与原型,获取bean类型,bean 别名的方法 。它最主要的方法就是getBean(String beanName)

    BeanFactory 三个子接口

    * HierarchicalBeanFactory:提供父容器的访问功能
    * ListableBeanFactory:提供了批量获取Bean的方法
    * AutowireCapableBeanFactory:在BeanFactory基础上实现对已存在实例的管理
    ConfigurableBeanFactory
    主要单例bean的注册,生成实例,以及统计单例bean
    ConfigurableListableBeanFactory
    继承了上述的所有接口,增加了其他功能:比如类加载器,类型转化,属性编辑器,BeanPostProcessor,作用域,bean定义,处理bean依赖关系, bean如何销毁…
    实现类 DefaultListableBeanFactory
    实现了ConfigurableListableBeanFactory,实现上述BeanFactory所有功能。它还可以注册BeanDefinition

    四、 ApplicationContext 介绍

    如果说BeanFactory是Sping的心脏,那么ApplicationContext就是完整的身躯了
    ApplicationContext结构图.png

    ApplicationContext类结构树.png

     Spring 具有非常大的灵活性,它提供了三种主要的装配机制

    •  在 XML 中进行显示配置
    • 在 Java 中显示配置
    • 隐式的 bean 发现机制和自动装配
      •   组件扫描 (component scanning) : Spring 会自动发现应用上下文中创建的 bean
      •   自动装配(autowire):Spring 自动满足 bean 之间的依赖
    (使用的优先性: 3>2>1)尽可能地使用自动配置的机制,显示配置越少越好。当必须使用显示配置bean的时候(如:有些源码不是由你来维护的,而当你需要为这些代码配置bean的时候),推荐使用类型安全比XML更加强大的JavaConfig。最后只有当你想要使用便利的XML命名空间,并且在JavaConfig中没有同样的实现时,才使用XML。
    1. 通过xml文件将配置加载到IOC容器中
    <?xml version="1.0" encoding="UTF-8"?>
    <beans xmlns="http://www.springframework.org/schema/beans"
           xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
           xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd">
         <!--若没写id,则默认为com.test.Man#0,#0为一个计数形式-->
        <bean id="man" class="com.test.Man"></bean>
    </beans>
    public class Test {
        public static void main(String[] args) {
            //加载项目中的spring配置文件到容器
            //ApplicationContext context = new ClassPathXmlApplicationContext("resouces/applicationContext.xml");
            //加载系统盘中的配置文件到容器
            ApplicationContext context = new FileSystemXmlApplicationContext("E:/Spring/applicationContext.xml");
            //从容器中获取对象实例
            Man man = context.getBean(Man.class);
            man.driveCar();
        }
    }
    1. 通过java注解的方式将配置加载到IOC容器
    //同xml一样描述bean以及bean之间的依赖关系
    @Configuration
    public class ManConfig {
        @Bean
        public Man man() {
            return new Man(car());
        }
        @Bean
        public Car car() {
            return new QQCar();
        }
    }
    public class Test {
        public static void main(String[] args) {
            //从java注解的配置中加载配置到容器
            ApplicationContext context = new AnnotationConfigApplicationContext(ManConfig.class);
            //从容器中获取对象实例
            Man man = context.getBean(Man.class);
            man.driveCar();
        }
    }
    1. 隐式的bean发现机制和自动装配
    /**
     * 这是一个游戏光盘的实现
     */
    //这个简单的注解表明该类回作为组件类,并告知Spring要为这个创建bean。
    @Component
    public class GameDisc implements Disc{
        @Override
        public void play() {
            System.out.println("我是马里奥游戏光盘。");
        }
    }

    不过,组件扫描默认是不启用的。我们还需要显示配置一下Spring,从而命令它去寻找@Component注解的类,并为其创建bean

    @Configuration
    @ComponentScan
    public class DiscConfig {
    }
    我们在DiscConfig上加了一个@ComponentScan注解表示在Spring中开启了组件扫描,默认扫描与配置类相同的包,就可以扫描到这个GameDisc的Bean了。这就是Spring的自动装配机制。

    除了提供BeanFactory所支持的所有功能外ApplicationContext还有额外的功能

    • 默认初始化所有的Singleton,也可以通过配置取消预初始化。
    • 继承MessageSource,因此支持国际化。
    • 资源访问,比如访问URL和文件。
    • 事件机制。
    • 同时加载多个配置文件。
    • 以声明式方式启动并创建Spring容器。

    参考:https://www.jianshu.com/p/2854d8984dfc

  • 相关阅读:
    当前日志损坏解决一例
    Oracle 1204 RAC failover 测试 (一)
    Logical standby跳过个别SQL不Apply的测试
    Data guard 又出问题了
    CPIO无反应
    回答棉花糖先生关于我说的DB自动增加Index的问题
    SSD硬盘,先不要用在Server上
    ORA00304: requested INSTANCE_NUMBER is busy,终于解决
    .Net运行时的相互关系
    CSS布局探密04
  • 原文地址:https://www.cnblogs.com/baizhuang/p/11978517.html
Copyright © 2020-2023  润新知