IoC容器7——bean定义继承

bean定义继承

一个bean定义可包含不少配置信息,包括构造函数参数,属性值和容器特定信息例如初始化方法、静态工厂方法名等等。一个子bean定义从父bean定义继承配置数据。子bean定义能够根据须要覆盖一些值或者增长其它值。使用父、子bean定义能够节省许多代码输入。实际上,这是模版的一种形式。spring

若是编程的方式使用ApplicationContext接口,子bean定义被表示为ChildBeanDefinition类。大多数用户不在这个级别上使用它,而是以声明的方式配置bean定义在(例如)ClassPathXmlApplicationContext中。当使用基于XML的配置元数据,使用parent属性代表是一个子bean定义,设置这个属性的值为parent bean。编程

<bean id="inheritedTestBean" abstract="true"
        class="org.springframework.beans.TestBean">
    <property name="name" value="parent"/>
    <property name="age" value="1"/>
</bean>

<bean id="inheritsWithDifferentClass"
        class="org.springframework.beans.DerivedTestBean"
        parent="inheritedTestBean" init-method="initialize">
    <property name="name" value="override"/>
    <!-- the age property value of 1 will be inherited from parent -->
</bean>

若是没有指定class属性,子bean定义使用父bean定义的class属性,可是也能够覆盖。在后一种状况下,子bean的类必须于父bean的类兼容,即它必须能够接受父bean的属性值。ide

子bean定义从父bean定义继承做用域、构造函数参数值、属性值和方法覆盖,并添加新值。任何对做用域、初始化方法、销毁方法和静态工厂方法的设置会覆盖相关父定义的设置。函数

------其它的设置老是从子定义获取,包括:依赖关系、自动装配模式、依赖关系检查、单例、懒加载初始化。---------code

上例中经过使用abstract属性明确指出了父bean定义是抽象的。若是父定义没有指定class属性,就须要明确的标记bean定义是抽象的。例如:继承

<bean id="inheritedTestBeanWithoutClass" abstract="true">
    <property name="name" value="parent"/>
    <property name="age" value="1"/>
</bean>

<bean id="inheritsWithClass" class="org.springframework.beans.DerivedTestBean"
        parent="inheritedTestBeanWithoutClass" init-method="initialize">
    <property name="name" value="override"/>
    <!-- age will inherit the value of 1 from the parent bean definition-->
</bean>

父bean因为不完整而不能被实例化,它也须要明确的标记为abstract。当一个bean定义是抽象的,它仅仅能用做纯模版bean定义,做为子定义的父定义。尝试经过引用它做为另外一个bean的引用属性或使用id进行显示的getBean()调用来使用一个抽象的父bean会返回一个错误。类似的,容器内部的preInstantiateSingletons()方法会忽略抽象的bean定义。接口

ApplicationContext默认预实例化全部的singleton。所以,若是有一个(父)bean定义打算仅看成模版使用而且这个bean定义指定了类,保证设置abstract属性为true是很是重要的(至少对singleton bean),不然应用上下文会尝试预实例化抽象bean。作用域

相关文章
相关标签/搜索