Spring中lazy-init属性

Spring中lazy-init属性

1. 在 Spring 框架中的 lazy-init 属性

在 Spring 框架中,lazy-init 属性主要用于控制 Spring 容器中 Bean 的初始化时机。

含义: 当一个 Bean 被定义在 Spring 的配置文件(可以是 XML 配置或者基于注解的配置等效场景)中时,通过设置 lazy-init 属性,可以指定这个 Bean 是在 Spring 容器启动时就立即初始化,还是等到第一次被使用时才进行初始化。

取值及作用

  • false(默认值,在某些早期版本中可能是 true,但现在普遍默认 false:当 lazy-init="false" 时,意味着在 Spring 容器启动过程中,一旦解析到该 Bean 的定义,就会立即对其进行初始化操作。初始化操作包括创建 Bean 的实例、执行依赖注入(如果有)、调用初始化方法(如果配置了)等一系列步骤。例如,对于一个数据库连接池的 Bean,如果设置为 false,那么在容器启动时就会提前创建好连接池实例,准备好供后续业务使用。

  • true:若 lazy-init="true",则该 Bean 不会在 Spring 容器启动时初始化。而是等到应用程序中第一次真正需要使用这个 Bean 时,Spring 容器才会对其进行初始化操作。比如,有一个用于处理特定业务逻辑且使用频率不高的 Bean,设置为 lazy-init="true" 后,就可以节省容器启动时不必要的资源消耗和初始化时间,只有当该业务逻辑真正被触发需要这个 Bean 时,它才会被初始化并投入使用。

2. 代码控制
基于 XML 配置方式

在传统的 XML 配置文件中,可以在<bean>元素里设置lazy-init属性来控制 Bean 的初始化时机。

示例如下:

 <?xml version="1.0" encoding="UTF-8"?>
 <beans xmlns="http://www.springframework.org/schema/beans"
        xmlns:xsi="http://www.springframework.org/schema/xsi"
        xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsi">
 ​
     <!-- 定义一个普通的Bean,设置为立即初始化(默认情况) -->
     <bean id="normalBean" class="com.example.demo.NormalBean">
         <!-- 这里可以设置其他属性和依赖注入等 -->
     </bean>
 ​
     <!-- 定义一个延迟初始化的Bean -->
     <bean id="lazyInitBean" class="com.example.demo.LazyInitBean" lazy-init="true">
         <!-- 同样可以设置其他属性和依赖注入等 -->
     </bean>
 ​
 </beans>

在上述示例中:

  • normalBean 没有显式设置 lazy-init 属性,所以它会按照默认情况(在 Spring 版本较新时默认值为 false,即立即初始化)在 Spring 容器启动时就进行初始化。

  • lazyInitBean 则通过设置 lazy-init="true",会在容器启动时不进行初始化,而是等到第一次被使用时才进行初始化。

基于注解配置方式

Spring 也提供了注解来实现类似的功能,常用的注解有 @Component@Service@Repository@Controller 等,这些注解用于标识不同类型的组件(类),可以结合 @Lazy 注解来控制 lazy-init 属性。

示例如下:

 package com.example.demo;
 ​
 import org.springframework.context.annotation.Component;
 import org.springframework.context.annotation.Lazy;
 ​
 // 这是一个普通的组件类,默认会在容器启动时初始化
 @Component
 public class NormalComponent {
     // 类的内部实现
 }
 ​
 // 这是一个延迟初始化的组件类
 @Component
 @Lazy(true)
 public class LazyComponent {
     // 类的内部实现
 }

在上述示例中:

  • NormalComponent 类只使用了 @Component 注解,它会按照默认情况(类似于 XML 配置中的默认 lazy-init="false")在容器启动时就被初始化。

  • LazyComponent 类除了使用 @Component 注解标识自己是一个组件外,还使用了 @Lazy(true) 注解,这就相当于设置了 lazy-init="true",使得该类在 Spring 容器启动时不会被初始化,而是等到第一次被使用时才进行初始化。

另外,如果是在 Spring Boot 项目中,很多时候会使用 @SpringBootApplication 启动类注解来自动扫描组件。上述的基于注解的配置方式同样适用,只要在需要延迟初始化的类上添加相应的注解即可。

基于 Java 配置类方式

除了 XML 和注解配置外,还可以通过 Java 配置类来设置 lazy-init 属性。

首先创建一个 Java 配置类:

 package com.example.demo;
 ​
 import org.springframework.context.annotation.Bean;
 import org.springframework.context.annotation.Configuration;
 import org.springframework.context.annotation.Lazy;
 ​
 @Configuration
 public class AppConfig {
 ​
     // 定义一个立即初始化的Bean
     @Bean
     public NormalBean normalBean() {
         return new NormalBean();
     }
 ​
     // 定义一个延迟初始化的Bean
     @Bean
     @Lazy(true)
     public LazyBean lazyBean() {
         return new LazyBean();
     }
 }

在上述示例中:

  • normalBean() 方法定义了一个普通的 Bean,它会按照默认情况(类似于 XML 配置中的默认 lazy-init="false")在容器启动时就被初始化。

  • lazyBean() 方法定义了一个延迟初始化的 Bean,通过添加 @Lazy(true) 注解,相当于设置了 lazy-init="true",使得该 Bean 在容器启动时不会被初始化,而是等到第一次被使用时才进行初始化。

通过以上几种方式,就可以在 Spring 框架中根据具体需求在代码中灵活控制 lazy-init 属性,以达到优化资源利用和提升应用性能的目的。

### Spring框架中Bean作用域(Scope)的默认值 在Spring框架中,Bean的作用域(Scope)用于定义 Bean 的生命周期及其可见范围。若未显式指定 `@Scope` 注解或 XML 配置中的 `scope` 属性,则 Spring 会使用 `"singleton"` 作为默认作用域[^2]。 这意味着,在大多数情况下,Spring 容器将只为该 Bean 创建一个共享的实例,并在整个应用上下文中提供对该实例的引用。此行为适用于通过注解(如 `@Component`、`@Service`)或 XML 配置定义的 Bean,只要未明确设置其他作用域,都会以单例模式进行管理[^1]。 例如,以下 Java 注解配置中并未指定 `@Scope`: ```java @Component public class MyService { // 默认作用域为 singleton } ``` 在此示例中,`MyService` 将被 Spring 容器作为单例 Bean 管理,所有对该 Bean 的请求都将返回相同的实例[^2]。 同样地,在 XML 配置文件中省略 `scope` 属性时,默认也为 `singleton`: ```xml <bean id="myBean" class="com.example.MyBean"/> <!-- 等价于 scope="singleton" --> ``` 这种设计适用于无状态组件或需要全局共享的状态对象,是 Spring 中最常用的作用域之一[^4]。 --- ### 单例作用域的特点 - **唯一实例**:每个 Spring 应用上下文中仅存在一个该 Bean 的实例。 - **容器管理生命周期**:Bean 的创建和销毁由 Spring 容器控制,通常与上下文的启动和关闭同步。 - **资源共享**:适合存储全局状态或共享资源,如数据库连接池、缓存服务等。 --- ### 其他常见作用域简介 虽然 `singleton` 是默认作用域,Spring 还支持多种其他作用域,包括: - `prototype`:每次请求都会创建一个新的实例。 - `request`:每个 HTTP 请求拥有独立的 Bean 实例(仅限 Web 应用)。 - `session`:每个 HTTP Session 拥有一个独立的 Bean 实例(仅限 Web 应用)。 - `application`:每个 ServletContext 生命周期内只有一个实例(仅限 Web 应用)。 - `websocket`:每个 WebSocket 会话周期内只有一个实例(仅限 WebSocket 应用)。 这些作用域可以通过 `@Scope("prototype")` 或在 XML 配置中指定 `scope` 属性来启用[^3]。 --- ### 自定义作用域的注册方式 Spring 提供了扩展机制,允许开发者自定义作用域并通过 `ConfigurableBeanFactory#registerScope` 方法将其注册到容器中。例如: ```java ConfigurableBeanFactory beanFactory = ...; beanFactory.registerScope("customScope", new CustomScope()); ``` 该方法可用于实现特定业务场景下的作用域管理,如线程级作用域、任务作用域等。 ---
评论
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符
 
红包 添加红包
表情包 插入表情
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值