IoC 容器概述

IoC 容器

简介

Spring 的控制反转 (IoC) 容器。IoC 也称为依赖注入 (DI)。这是一个过程。对象仅通过构造函数参数、工厂方法的参数设置的属性来定义它们的依赖关系, 然后容器在创建 bean 时注入这些依赖项。

在IoC模式下,控制权发生了反转,即从开发人员自己创建转移到了IoC容器,所有组件不再由应用程序自己创建和配置,而是由IoC容器负责,所以叫控制反转。

BeanFactory 接口提供了一种高级配置机制,能够管理任何类型的对象。 ApplicationContext 是 的子接口BeanFactory。它补充说:

  • 更容易与 Spring 的 AOP 功能集成
  • 消息资源处理(用于国际化)
  • 活动发布
  • 应用层特定上下文,例如WebApplicationContext 用于 Web 应用程序的上下文。

简而言之,它BeanFactory提供了配置框架和基本功能,并ApplicationContext增加了更多的企业特定功能。

在 Spring 中,由 Spring IoC 容器管理的对象称为 bean。bean 是由 Spring IoC 容器实例化、组装和管理的对象。否则,bean 只是应用程序中的众多对象之一。Bean 以及它们之间的依赖关系反映在容器使用的配置元数据中。

容器概述

ApplicationContext`接口代表 Spring IoC 容器,负责实例化、配置和组装 bean。容器通过读取配置元数据来获取关于要实例化、配置和组装哪些对象的指令。配置元数据以 XML、Java 注释或 Java 代码表示。它允许您表达组成应用程序的对象以及这些对象之间丰富的相互依赖关系。

ApplicationContextSpring 提供了该接口的几个实现。在独立应用程序中,通常会创建ClassPathXmlApplicationContext 或的实例 FileSystemXmlApplicationContext。虽然 XML 一直是定义配置元数据的传统格式,但您可以通过提供少量 XML 配置来以声明方式启用对这些附加元数据格式的支持,从而指示容器使用 Java 注释或代码作为元数据格式。

配置元数据

Spring IoC 容器使用一种形式的配置元数据。此配置元数据表示您作为应用程序开发人员如何告诉 Spring 容器实例化、配置和组装应用程序中的对象。

配置元数据传统上以简单直观的 XML 格式提供,本章大部分内容都使用这种格式来传达 Spring IoC 容器的关键概念和特性。

有关在 Spring 容器中使用其他形式的元数据的信息,请参阅:

Spring 配置包含容器必须管理的至少一个,通常是多个 bean 定义。基于 XML 的配置元数据将这些 bean 配置为<bean/>顶级元素内的<beans/>元素。Java 配置通常@Bean在类中使用 -annotated 方法@Configuration

实例化一个容器

提供给构造函数的一个或多个位置路径ApplicationContext是资源字符串,允许容器从各种外部资源(例如本地文件系统、Java 等)加载配置元数据。

ApplicationContext context = new ClassPathXmlApplicationContext("services.xml", "daos.xml");
编写基于 XML 的配置元数据

让 bean 定义多个 XML 文件会很有用。通常,每个单独的 XML 配置文件都代表架构中的一个逻辑层或模块。

<beans>
    <import resource="services.xml"/>
    <import resource="resources/messageSource.xml"/>
 
    <bean id="bean1" class="..."/>
</beans>
使用容器

ApplicationContext是一个高级工厂的接口,能够维护不同 bean 及其依赖项的注册表。

// create and configure beans
ApplicationContext context = new ClassPathXmlApplicationContext("services.xml", "daos.xml");

// retrieve configured instance
PetStoreService service = context.getBean("petStore", PetStoreService.class);

// use configured instance
List<String> userList = service.getUsernameList();

Bean概述

Spring IoC 容器管理一个或多个 bean。这些 bean 是使用您提供给容器的配置元数据创建的。

在容器本身中,这些 bean 定义表示为BeanDefinition 对象,其中包含(以及其他信息)以下元数据:

  • 一个包限定的类名:通常是被定义的 bean 的实际实现类。
  • Bean 行为配置元素,它说明 bean 在容器中的行为方式(范围、生命周期回调等)。
  • 对 bean 完成工作所需的其他 bean 的引用。这些引用也称为协作者或依赖项。
  • 要在新创建的对象中设置的其他配置设置——例如,池的大小限制或在管理连接池的 bean 中使用的连接数。

注意:

Bean 元数据和手动提供的单例实例需要尽早注册,官方不支持在运行时注册新 bean,并可能导致并发访问异常、bean 容器中的状态不一致。

命名 Bean

每个 bean 都有一个或多个标识符。这些标识符在承载 bean 的容器中必须是唯一的。一个 bean 通常只有一个标识符。但是,如果它需要多个,则可以将多余的视为别名。

在基于 XML 的配置元数据中,您可以使用id属性、name属性或两者来指定 bean 标识符。

您不需要为 bean 提供 name或 id。如果您不显式提供 nameid,则容器会为该 bean 生成一个唯一名称。但是,如果您想通过名称引用该 bean,通过使用ref元素或服务定位器样式查找,您必须提供名称。

实例化 Bean

bean 定义本质上是创建一个或多个对象的方法。

如果您使用基于 XML 的配置元数据,您可以在元素的class属性中指定要实例化的对象的类型。

您可以通过以下两种方式之一使用该属性:

  • 通常,在容器本身通过反射调用其构造函数直接创建 bean 的情况下,指定要构造的 bean 类,有点等价于 Java 代码中的new运算符。
  • static指定包含被调用以创建对象 的工厂方法的实际类,在不太常见的情况下,容器调用static类上的工厂方法来创建 bean。调用static工厂方法返回的对象类型可能是同一个类,也可能完全是另一个类。
使用构造函数进行实例化

当您通过构造方法创建 bean 时,所有普通类都可以被 Spring 使用并兼容。也就是说,正在开发的类不需要实现任何特定的接口或以特定的方式进行编码。只需指定 bean 类就足够了。但是,根据您用于该特定 bean 的 IoC 类型,您可能需要一个默认(空)构造函数。

<bean id="exampleBean" class="examples.ExampleBean"/>
使用静态工厂方法进行实例化

在定义使用静态工厂方法创建的 bean 时,使用class 属性指定包含static工厂方法的类,使用命名属性factory-method指定工厂方法本身的名称。您应该能够调用此方法(使用可选参数,如后所述)并返回一个活动对象,该对象随后被视为是通过构造函数创建的。这种 bean 定义的一种用途是static在遗留代码中调用工厂。

<bean id="clientService"
    class="examples.ClientService"
    factory-method="createInstance"/>
使用实例工厂方法进行实例化

与通过静态工厂方法进行实例化类似,使用实例工厂方法进行实例化会从容器中调用现有 bean 的非静态方法来创建新 bean。要使用此机制,请将class属性留空,并在factory-bean属性中指定当前(或父级或祖先)容器中包含要调用以创建对象的实例方法的 bean 的名称。factory-method使用属性设置工厂方法本身的名称。以下示例显示了如何配置这样的 bean:

<!-- the factory bean, which contains a method called createInstance() -->
<bean id="serviceLocator" class="examples.DefaultServiceLocator">
    <!-- inject any dependencies required by this locator bean -->
</bean>

<!-- the bean to be created via the factory bean -->
<bean id="clientService"
    factory-bean="serviceLocator"
    factory-method="createClientServiceInstance"/>
public class DefaultServiceLocator {

    private static ClientService clientService = new ClientServiceImpl();

    public ClientService createClientServiceInstance() {
        return clientService;
    }
}
  • 1
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

吕布辕门

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值