并发
https://blog.csdn.net/qq_15846805/article/details/78095693
spring中的bean默认是单例的,这样如果我们写的bean是有状态的就会产生线程安全问题,有状态的bean就是指类中存在实例变量,服务器会为每个请求开一个线程,这样当一个线程修改了实例变量,另一个线程访问的变量就是被修改过的,这就是线程不安全的。
我们以controller为例,下面是测试代码
···
@Controller
public class testController {
private int i=0;
@RequestMapping("test")
public ModelAndView test( ){
ModelAndView mav=new ModelAndView("test");
mav.addObject("test", i++);
return mav;
}
}
···
前台通过${test }获取值。分别发送三次请求,前台页面取得的值为 :
0 1 2
若想在线程安全情况下使用有状态的bean有以下两种方法:
第一种在@controller之前加上@Scope("prototype"),将spring中的bean改为多例。
前台通过${test }获取值。分别发送三次请求,前台页面取得的值为 :
0 0 0
第二种使用threadLocal,代码如下
···
@Controller
public class testController {
ThreadLocal<Integer> i=new ThreadLocal<Integer>(){
@Override
protected Integer initialValue() {
return 0;
};
};
@RequestMapping("test")
public ModelAndView test( ){
ModelAndView mav=new ModelAndView("test");
mav.addObject("test", i.get());
i.set(i.get()+1);
return mav;
}
}
前台通过${test }获取值。分别发送三次请求,前台页面取得的值为 :
0 0 0
···当然在一般情况下我们使用无状态的bean,只需要将实例变量改为方法中的局部变量或者使用方法参数传递即可
https://www.cnblogs.com/leirenyuan/p/6016063.html