当前位置: 首页 > news >正文

Spring——和IoC相关的特性

目录

IoC中Bean的生命周期

实例化(Instantiation)

属性注入(Populate Properties)

初始化(Initialization)

使用(Bean in Use)

销毁(Destruction)

Lazy-init和预实例化

FactoryBean和BeanFactory

BeanFactory

FactoryBean

BeanPOSTProcessor的妙用

Spring的Autowiring

1. 使用autowire属性(XML配置):

2. 使用@Autowired注解(注解配置):

3. 使用@Resource注解(注解配置):

4. 使用Java配置类(Java配置):

Bean对IoC容器的感知


IoC中Bean的生命周期

Spring IOC 中 Bean 的⽣命周期⼤致分为四个阶段:实例化(Instantiation)、属性赋值(Populate)、初始化 (Initialization)、销毁(Destruction)。

  1. 实例化(Instantiation)
    当容器启动时,它会创建Bean的实例。这个阶段包括对象的构造函数调用。
  2. 属性注入(Populate Properties)
    容器会通过属性注入(Dependency Injection)来设置Bean的属性值。这通常包括依赖关系的注入,如通过构造函数注入或setter方法注入依赖的对象。
  3. 初始化(Initialization)
    如果Bean实现了InitializingBean接口,容器会调用其afterPropertiesSet方法。或者,如果Bean配置了init-method,容器也会在此时调用指定的初始化方法。
  4. 使用(Bean in Use)
    Bean实例现在处于可用状态,可以被其他Bean引用和使用。
  5. 销毁(Destruction)
    当容器关闭或不再需要Bean实例时,容器会销毁Bean实例。这个阶段包括对象的销毁和资源的释放。
Lazy-init和预实例化

在Spring的IoC容器中,可以通过两种方式来控制Bean的初始化时机:Lazy Initialization(延迟初始化)和Eager Initialization(预实例化)。这两种方式决定了容器在启动时是否立即实例化和初始化Bean。

  1. Lazy Initialization(延迟初始化): 在延迟初始化中,Bean实例仅在第一次访问时才会被实例化和初始化。这意味着容器在启动时不会创建所有Bean实例,而只有在需要时才会创建。这可以减少启动时间和系统资源的消耗。BeanFactory是延迟加载。

  2. Eager Initialization(预实例化): 在预实例化中,容器在启动时会创建并初始化所有Bean实例,即使这些Bean可能在后续的应用程序执行过程中并不会被立即使用。这可以确保所有Bean在应用程序启动时都处于可用状态,但可能会增加启动时间和系统资源的消耗。

    预实例化是默认行为,如果不明确配置延迟初始化,容器将采用预实例化方式。如果需要显式配置Bean为延迟初始化,可以参考上述的lazy-init配置。ApplicationContext是预加载。

FactoryBean和BeanFactory
BeanFactory
  1. BeanFactory 是Spring框架的核心接口之一,它是IoC容器的底层基础。它的主要作用是管理Bean的生命周期,包括实例化、依赖注入、初始化和销毁等。

  2. BeanFactory 是一个工厂接口,它定义了访问和管理Bean的方法,包括 getBeancontainsBeanisSingletonisPrototype 等。

  3. BeanFactory 不负责Bean的创建,而是负责Bean的获取和生命周期管理。它是IoC容器的核心接口,提供了基本的Bean管理功能。

FactoryBean
  1. FactoryBean 也是Spring框架中的一个接口,但它的作用不同于 BeanFactoryFactoryBean 用于创建和管理特定类型的Bean,通常是复杂的或自定义的Bean。

  2. FactoryBean 接口要求实现类必须实现 getObject 方法,该方法定义了如何创建和返回Bean实例。

  3. FactoryBean 的实现类通常被称为"工厂Bean",它负责创建其他Bean的实例,这些Bean的类型可以与工厂Bean不同。

  4. 通过实现 FactoryBean 接口,你可以自定义Bean的创建逻辑,将其封装在工厂Bean中,然后将工厂Bean注册到Spring容器中。

总的来说,BeanFactory 是Spring容器的核心接口,用于管理Bean的生命周期,而 FactoryBean 是用于创建和管理特定类型的Bean的接口。FactoryBean 允许你封装复杂的Bean创建逻辑,而 BeanFactory 负责整个容器的基本Bean管理。在实际开发中,你会更频繁地与 BeanFactory 打交道,而 FactoryBean 则用于特殊需求下的自定义Bean创建。

BeanPOSTProcessor的妙用

BeanPostProcessor 是Spring框架中的一个接口,用于扩展和自定义Bean的初始化过程。通过实现 BeanPostProcessor 接口,你可以在容器实例化、依赖注入和初始化Bean的过程中插入自定义的处理逻辑。这些处理逻辑可以在Bean的初始化之前和之后执行,允许你对Bean进行额外的处理。

BeanPostProcessor 接口定义了以下两个方法:

  1. postProcessBeforeInitialization(Object bean, String beanName) 在Bean的初始化之前被调用。你可以在这个方法中进行一些前置处理,如修改Bean的属性值或检查Bean的状态。

  2. postProcessAfterInitialization(Object bean, String beanName) 在Bean的初始化之后被调用。你可以在这个方法中进行一些后置处理,如注册Bean的代理、包装Bean等

简单示例:

import org.springframework.beans.factory.config.BeanPostProcessor;
​
public class CustomBeanPostProcessor implements BeanPostProcessor {
​@Overridepublic Object postProcessBeforeInitialization(Object bean, String beanName) {// 在初始化之前执行的逻辑if (bean instanceof MyBean) {MyBean myBean = (MyBean) bean;myBean.setSomeProperty("Modified Value");}return bean;}
​@Overridepublic Object postProcessAfterInitialization(Object bean, String beanName) {// 在初始化之后执行的逻辑return bean;}
}
​

要使用自定义的 BeanPostProcessor,你需要将其注册到Spring容器中。这可以通过XML配置文件或Java配置类来完成,如下所示:

<bean class="com.elaine.CustomBeanPostProcessor"/>

或者在Java配置类中:

@Configuration
public class AppConfig {
​@Beanpublic CustomBeanPostProcessor customBeanPostProcessor() {return new CustomBeanPostProcessor();}
}

通过注册 BeanPostProcessor,你可以在Bean的初始化过程中执行自定义的处理逻辑,从而实现对Bean的扩展和定制。这对于AOP、事务管理、日志记录等方面非常有用。

Spring的Autowiring

Spring的自动装配(Autowiring)是一种机制,它允许Spring容器自动为Bean注入依赖。这样,你无需手动指定依赖关系,Spring会根据类型、名称或其他规则自动完成依赖注入。自动装配可以通过XML配置、注解和Java配置来实现,以下是一些示例:

1. 使用autowire属性(XML配置):

在XML配置文件中,可以使用autowire属性来指定自动装配方式。以下是一些autowire属性的取值:

  • no(默认值):不进行自动装配,你需要显式地配置依赖关系。

  • byName:按照属性名进行自动装配,容器会查找和属性名匹配的Bean,并注入到属性中。

  • byType:按照属性的数据类型进行自动装配,容器会查找和属性类型匹配的Bean,并注入到属性中。

  • constructor:类似byType,但是用于构造函数的参数自动装配。

<bean id="user" class="com.elaine.User" autowire="byName"><!-- user类的属性会自动装配 -->
</bean>
2. 使用@Autowired注解(注解配置):

通过@Autowired注解,你可以在类的字段、构造函数或方法上标记需要自动装配的依赖。

@Component
public class UserService {
​@Autowiredprivate UserDao userDao;
​public void saveUser(User user) {userDao.saveUser(user)}// ...
}
3. 使用@Resource注解(注解配置):

@Resource注解也可以用于自动装配,它支持按照Bean的名称或类型来查找依赖。

@Component
public class CustomerService {
​@Resourceprivate UserService userService;
​// ...
}
4. 使用Java配置类(Java配置):

通过Java配置类,你可以使用@Autowired注解和@Bean注解来定义Bean并注入依赖。

@Configuration
@ComponentScan(basePackages = "com.elaine")
public class AppConfig {
​@Autowiredprivate DataConnection dataConnecttion;
​@Beanpublic DataSource dataSource(DataConnection dataConnecttion) {return new DataSource(dataConnecttion);}
}

自动装配的具体实现依赖于Spring容器的类型和配置方式。Spring会根据配置和注解来识别依赖关系,并自动完成依赖注入。这提高了应用程序的可维护性和可扩展性,减少了手动配置的工作量。

Bean对IoC容器的感知

当一个Bean实现了Spring框架的 org.springframework.beans.factory.BeanNameAwareorg.springframework.beans.factory.BeanFactoryAware 接口时,它可以获得对IoC容器的一定程度的"感知"。这意味着该Bean可以获取关于自己的一些信息或与容器交互(在Bean中直接对IoC容器进行操作)。

以下是这两个接口的作用:

  1. BeanNameAware 接口: 当一个Bean实现 BeanNameAware 接口时,Spring容器在将Bean实例化后,会调用该Bean的 setBeanName(String name) 方法,并将该Bean在容器中的名称(ID)作为参数传递给方法。这样,Bean就可以获得自己在容器中的名称。

  2. BeanFactoryAware 接口: 当一个Bean实现 BeanFactoryAware 接口时,Spring容器在将Bean实例化后,会调用该Bean的 setBeanFactory(BeanFactory beanFactory) 方法,并将容器的Bean工厂作为参数传递给方法。这允许Bean与容器进行更多的交互,例如获取其他Bean实例。

http://www.lryc.cn/news/195039.html

相关文章:

  • 在 TensorFlow 中调试
  • 想要精通算法和SQL的成长之路 - 连续的子数组和
  • 【C++】头文件chrono
  • Python学习六
  • Springboot 集成 WebSocket
  • 谨以此篇,纪念我2023年曲折的计算机保研之路
  • VSS、VDD、VBAT、VSSA
  • 【Rust基础③】方法method、泛型与特征
  • 48.排列问题求解
  • 18.(开发工具篇Gitlab)Git如何回退到指定版本
  • IDEA初始配置
  • WM_COPYDATA传回返回值的一个方案
  • 【日常业务开发】接口性能优化
  • Android 10.0 禁止弹出系统simlock的锁卡弹窗功能实现
  • VulnHub lazysysadmin
  • ppt怎么压缩到10m以内?分享ppt缩小方法
  • 智能警用装备管理系统-科技赋能警务
  • 攻防千层饼
  • 组件封装使用?
  • 2.3 初探Hadoop世界
  • Flutter笔记:发布一个电商中文货币显示插件Money Display
  • 解密zkLogin:探索前沿的Sui身份验证解决方案
  • js构造函数
  • 性能测试-redis常见问题
  • 预测:2024 年将是互联网永远改变的一年。
  • Vue2 与 React 的区别
  • 【AI视野·今日Robot 机器人论文速览 第五十一期】Tue, 10 Oct 2023
  • 零经验想跳槽转行网络安全,需要准备什么?
  • Rust-是否使用Rc<T>
  • 论文解析——一种面向Chiplet互连的高效传输协议设计与实现