P67 面试必背!BeanFactory vs ApplicationContext 核心区别
面试题:BeanFactory 和 ApplicationContext 有什么区别?为什么都用 ApplicationContext?
1. 先说关系
text
ApplicationContext 是 BeanFactory 的子接口(扩展了它)
BeanFactory 是最底层的 IoC 容器,ApplicationContext 是增强版容器2. 核心区别
| 对比项 | BeanFactory | ApplicationContext |
|---|---|---|
| 定位 | IoC 容器的最基本接口 | 企业级应用容器 |
| Bean 加载时机 | 懒加载(getBean 时才创建) | 启动时预实例化单例 Bean(默认 eager) |
| 功能 | 只管理 Bean 的生命周期/依赖 | 扩展:AOP、事件发布、国际化、资源加载、环境抽象 |
| 扩展点 | 少 | 多(BeanPostProcessor 自动注册等) |
| 使用 | 极少直接用(内部/嵌入式场景) | 开发/SpringBoot 默认 |
3. ApplicationContext 的增强能力
- 事件机制:
ApplicationEventPublisher+@EventListener(观察者模式); - 国际化(i18n):MessageSource;
- 资源加载:
Resource抽象,统一 classpath/file/URL 访问; - 环境抽象:
Environment/PropertySource(配置管理); - 自动注册后处理器:BeanFactoryPostProcessor、BeanPostProcessor 自动扫描注册;
- AOP 集成:自动代理支持。
4. 加载时机对比(重要)
java
// BeanFactory:懒加载,不 getBean 不创建
BeanFactory bf = new XmlBeanFactory(...);
bf.getBean("userService"); // 此时才创建
// ApplicationContext:启动时预创建所有单例
ApplicationContext ctx = new ClassPathXmlApplicationContext("app.xml");
// 启动阶段 singleton Bean 已创建完毕这也是为什么 SpringBoot 启动慢一点点但启动后访问快:Bean 都提前创建好了,错误也能启动时尽早暴露。
5. 加分点
- 追问"BeanFactory 什么时候用":嵌入式/资源受限场景,想省启动时间时;
- 追问"为什么 ApplicationContext 默认饿汉":尽早暴露配置/依赖错误,避免运行时才发现 Bean 创建失败;
- 提一句:
DefaultListableBeanFactory是最常用的 BeanFactory 实现,ApplicationContext 内部也组合/继承了它。
一句话总结
ApplicationContext 是 BeanFactory 的增强子接口:BeanFactory 只管 Bean 生命周期(懒加载),ApplicationContext 额外提供事件、AOP、国际化、资源/环境抽象,并启动时预创建单例,所以实际项目都用它。