spring生成對象默認是單例(也就是一個對象)的。經過scope屬性能夠更改成多例。java
<bean id="singleton" class="java.util.Date" scope="singleton"></bean> <!--單例-->
<bean id="prototype" class="java.util.Date" scope="prototype"></bean> <!--非單例-->web
用過SpringMVC和Struts2 都知道, Struts2是線程安全 ,由於Struts2是基於類的攔截,每次處理一個請求都會實例一個spring
action對象,全部也就不存在線程安全的問題。安全
而SpringMVC是基於方法的攔截,SpringMVC的每個controller默認爲單例類,所以每個request請求過來,系統會有原有的多線程
instance去處理,這樣不用每次都建立controller,減小了對象的建立,和垃圾回收的時間。app
可是因爲就建立一個controller的instance,當多線程調用它的時候,它 的instance便再也不是線程安全的了。ui
所以應避免在controller中定義實例變量。.net
有幾種解決方法:
一、在Controller中使用ThreadLocal變量
二、在spring配置文件Controller中聲明 scope="prototype",每次都建立新的controller
所在在使用spring開發web 時要注意,默認Controller、Dao、Service都是單例的。prototype
@Controller
@RequestMapping("/fui")
public class FuiController extends SpringController {
//這麼定義的話就是單例
@Controller
@Scope("prototype")
@RequestMapping("/fui")
public class FuiController extends SpringController {
//每次都建立線程