Spring Bean中的六种作用域你了解吗

 更新时间:2023年09月05日 10:55:50   作者:²º¹⁷旧人不必等  
Bean的作用域是指Bean实例的生命周期及可见性范围,Spring框架定义了6种作用域,本文就来和大家聊聊这6种作用域的定义与使用,希望对大家有所帮助

一、作用域是什么

Bean的作用域是指Bean实例的生命周期及可见性范围,Spring框架定义了以下6种作用域:

1.singleton:单例作用域,所有对该Bean的请求都返回同一个Bean实例。

2.prototype:原型作用域,每次请求时都创建一个新的Bean实例。

3.request:请求作用域,每个HTTP请求都会创建一个新的Bean实例,该Bean实例仅在当前请求内有效。

4.session:会话作用域,每个HTTP会话都会创建一个新的Bean实例,该Bean实例仅在当前会话内有效。

5.application:全局作用域,一个bean 定义对应于单个ServletContext 的生命周期。

6.websocket: HTTP WebSocket 作用域,一个bean 定义对应于单个websocket 的生命周期。

选择适当的作用域可以提高应用程序的性能和可维护性。

下面用一个例子来解释Bean的作用域:你和别人一起协同开发的代码中有个Bean不想别人改动,那就可以通过调整Bean的作用域来解决.

下面有两个用户张三和李四,张三呢 调用了公共对象,但是张三特意使用了 user2来接收,

此时李四也想使用这个对象;然后他们一起调用了,但是发现李四调用的时候这个Name也被修改成小猫了.这是为什么呢 张三明显创建了一个新对象

其实真实的情况是Spring的IoC容器有两种作用域模式,一种是IoC默认的singleton(单例作用域),一种是可手动修改的prototype(原型作用域 / 多例作用域),在默认情况下,IoC容器采用singleton,也就是所有人获取到的都是同一个Bean对象,这样效率会高很多.

所以当我们使用原型模式时这个问题就解决了

//张三
@Controller
public class UserController2 {
    @Autowired
    private User user;
    public void doMethod() {
        User user2 = user;
        System.out.println("UserController2 修改之前:User -> " + user);
        user2.setName("小猫");
        System.out.println("UserController2 修改之后:User -> " + user);
    }
}
//李四
@Controller
public class UserController3 {
    @Autowired
    private User user;
    public void doMethod() {
        System.out.println("UserController3:user -> " + user);
    }
}

1、singleton(单例作用域)

官⽅说明:(Default) Scopes a single bean definition to a single object instance for each Spring IoC container.

描述:该作⽤域下的Bean在IoC容器中只存在⼀个实例:获取Bean(即通过applicationContext.getBean等⽅法获取)及装配Bean(即通过@Autowired注⼊)都是同⼀个对象。

场景:通常⽆状态的Bean使⽤该作⽤域。⽆状态表示Bean对象的属性状态不需要更新

备注:Spring默认选择该作⽤域

2、prototype(原型作用域)

官⽅说明:Scopes a single bean definition to any number of object instances.

描述:每次对该作⽤域下的Bean的请求都会创建新的实例:获取Bean(即通过applicationContext.getBean等⽅法获取)及装配Bean(即通过@Autowired注⼊)都是新的对象实例。

场景:通常有状态的Bean使⽤该作⽤域

上图中,每个引用对应一个新的 bean 实例。

请注意,上图中的例子不适用于生产环境。因为 DAO 通常来说是无状态的 bean ,应该指定它的作用域为 singleton 比较合适

3、request(请求作用域)

官⽅说明:Scopes a single bean definition to the lifecycle of a single HTTP request. That is, each HTTP request has its own instance of a bean created off the back of a single bean definition. Only valid in the context of a web-aware Spring ApplicationContext.

描述:每次http请求会创建新的Bean实例,类似于prototype

场景:⼀次http的请求和响应的共享Bean

备注:限定SpringMVC中使⽤

4、session(回话作用域)

官⽅说明:Scopes a single bean definition to the lifecycle of an HTTP Session. Only valid in the context of a web-aware Spring ApplicationContext.

描述:在⼀个http session中,定义⼀个Bean实例

场景:⽤户回话的共享Bean, ⽐如:记录⼀个⽤户的登陆信息

备注:限定SpringMVC中使⽤

5、application(全局作用域)

官⽅说明:Scopes a single bean definition to the lifecycle of a ServletContext. Only valid in the context of a web-aware Spring ApplicationContext.

描述:在⼀个http servlet Context中,定义⼀个Bean实例

场景:Web应⽤的上下⽂信息,⽐如:记录⼀个应⽤的共享信息

备注:限定SpringMVC中使⽤

6、websocket( HTTP WebSocket 作用域)

官⽅说明:Scopes a single bean definition to the lifecycle of a WebSocket. Only valid in the context of a web-aware Spring ApplicationContext.

描述:在⼀个HTTP WebSocket的⽣命周期中,定义⼀个Bean实例

场景:WebSocket的每次会话中,保存了⼀个Map结构的头信息,将⽤来包裹客户端消息头。第⼀次初始化后,直到WebSocket结束都是同⼀个Bean。

备注:限定Spring WebSocket中使⽤

二、单例作⽤域VS 全局作⽤域

  • singleton 是 Spring Core 的作⽤域;application 是 Spring Web 中的作⽤域;
  • singleton 作⽤于 IoC 的容器,⽽ application 作⽤于 Servlet 容器。

三、设置作用域

singleton 作用域是 Spring 中默认的作用域,

使⽤ @Scope 标签就可以⽤来声明 Bean 的作⽤域,⽐如设置 Bean 的作⽤域,如下代码所示:

@Component
public class Users {
    @Scope(prototype)
    @Bean(name = "u")
    public User user() {
        User user = new User();
        user.setId(1);
        user.setName("Hi user"); 
        return user;
    }
}

@Scope 标签既可以修饰⽅法也可以修饰类,@Scope 有两种设置⽅式:

1. 直接设置值:@Scope("prototype")

2. 使⽤枚举设置:@Scope(ConfigurableBeanFactory.SCOPE_PROTOTYPE)

以上就是Spring Bean中的六种作用域你了解吗的详细内容,更多关于Bean作用域的资料请关注脚本之家其它相关文章!

相关文章

  • java集合类arraylist循环中删除特定元素的方法

    java集合类arraylist循环中删除特定元素的方法

    下面小编就为大家带来一篇Java集合类ArrayList循环中删除特定元素的方法。小编觉得挺不错的,现在就分享给大家,也给大家做个参考。一起跟随小编过来看看吧
    2016-11-11
  • 时间中间键的整理

    时间中间键的整理

    这篇文章主要介绍了时间中间键的整理的相关资料,如有疑问请留言或者到本站社区交流讨论,感谢阅读,希望能帮助到大家,需要的朋友可以参考下
    2017-10-10
  • java实现 二叉搜索树功能

    java实现 二叉搜索树功能

    这篇文章主要介绍了java实现 二叉搜索树功能,代码简单易懂,非常不错,具有一定的参考借鉴价值,需要的朋友可以参考下
    2018-07-07
  • Java反射机制原理、Class获取方式以及应用场景详解

    Java反射机制原理、Class获取方式以及应用场景详解

    反射机制是JAVA的核心知识点之一,大多数框架的实现原理就是利用了反射机制,掌握反射机制会使你学习框架更加轻松高效,这篇文章主要给大家介绍了关于Java反射机制原理、Class获取方式以及应用场景的相关资料,需要的朋友可以参考下
    2022-04-04
  • 详解SpringBoot 应用如何提高服务吞吐量

    详解SpringBoot 应用如何提高服务吞吐量

    这篇文章主要介绍了Spring Boot 应用如何提高服务吞吐量,文中通过示例代码介绍的非常详细,对大家的学习或者工作具有一定的参考学习价值,需要的朋友们下面随着小编来一起学习学习吧
    2020-07-07
  • Springboot的@Cacheable注解使用方法

    Springboot的@Cacheable注解使用方法

    @Cacheable 是 Spring 框架提供的一种基于缓存的注解,它可以被应用在方法上以指示该方法的结果需要被缓存起来,缓存在哪个 Cache 中以及该方法使用何种缓存键,以下代码展示了如何使用 @Cacheable 注解,感兴趣的朋友跟随小编一起看看吧
    2024-04-04
  • 从java源码分析线程池(池化技术)的实现原理

    从java源码分析线程池(池化技术)的实现原理

    这篇文章主要介绍了从java源码分析线程池(池化技术)的实现原理,池化技术是一种编程技巧,当程序出现高并发时,能够明显的优化程序,降低系统频繁创建销毁连接等额外开销,下文更多的相关介绍需要的小伙伴可以参考一下
    2022-04-04
  • java设计模式--三种工厂模式详解

    java设计模式--三种工厂模式详解

    这篇文章主要为大家详细介绍了Java设计模式之工厂模式,具有一定的参考价值,感兴趣的小伙伴们可以参考一下,希望能给你带来帮助
    2021-07-07
  • Spring自动装配与扫描注解代码详解

    Spring自动装配与扫描注解代码详解

    这篇文章主要介绍了Spring自动装配与扫描注解代码详解,具有一定借鉴价值,需要的朋友可以参考下。
    2017-12-12
  • Java 分析并解决内存泄漏的实例

    Java 分析并解决内存泄漏的实例

    这篇文章主要介绍了Java 分析并解决内存泄漏的实例,帮助大家更好的理解和学习Java,感兴趣的朋友可以了解下
    2020-08-08

最新评论