# 1.7 Bean的继承

bean定义可以包含很多配置信息，包括构造函数参数、属性值和容器特定的信息，例如初始化方法、静态工厂方法名等。子bean定义从父定义继承配置数据。子定义可以覆盖一些值，或者根据需要添加其他值。使用父bean和子bean定义可以节省大量的输入。实际上，这是一种templating。

如果以编程方式使用ApplicationContext接口，则子bean定义由ChildBeanDefinition类表示。大多数用户并不需要直接使用这个类。相反，他们在类（如ClassPathXmlApplicationContext）中声明性地配置bean定义。使用基于XML的配置元数据时，可以通过使用parent属性来表名这是一个子bean定义，并将父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>
```

如果没有指定bean类，则子bean定义使用父定义中的bean类，但也可以覆盖它。在后一种情况下，子bean类必须与父类兼容（即，它必须接受父类的属性值）。

子bean定义从父bean继承作用域、构造函数参数值、属性值和方法重写，并可以选择添加新值。指定的任何范围、初始化方法、销毁方法或静态工厂方法设置都将覆盖相应的父设置。

其余的设置总是取自子定义：依赖、自动装载模式、依赖项检查、singleton和lazy init。

前面的示例使用abstract属性显式地将父bean定义标记为abstract。如果父定义没有指定类，则需要显式地将父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不能单独实例化，因为它是不完整的，并且还显式地标记为抽象的。当定义是抽象的时，它只能用作纯模板bean定义，该定义用作子定义的父定义。试图单独使用这样一个抽象父bean，将其作为另一个bean的引用属性来引用，或者使用父bean id执行显式getbean（）调用，都会返回一个错误。类似地，容器的内部preInstantiateSingletons（）方法忽略定义为抽象的bean定义。

> 默认情况下，ApplicationContext预实例化所有单例。因此，重要的是（至少对于singleton bean而言），如果你有一个（父）bean定义，而该定义指定了一个类，那么你必须确保将abstract属性设置为true，否则应用程序上下文将实际（尝试）预实例化abstract bean。


---

# Agent Instructions: Querying This Documentation

If you need additional information that is not directly available in this page, you can query the documentation dynamically by asking a question.

Perform an HTTP GET request on the current page URL with the `ask` query parameter:

```
GET https://docs.flydean.com/spring-framework-documentation5/core-technologies/1.the-ioc-container/1.7bean-definition-inheritance.md?ask=<question>
```

The question should be specific, self-contained, and written in natural language.
The response will contain a direct answer to the question and relevant excerpts and sources from the documentation.

Use this mechanism when the answer is not explicitly present in the current page, you need clarification or additional context, or you want to retrieve related documentation sections.
