Spring MVC不要在@Service bean中保存狀態

先看這么一段代碼:

@Service
public class AccountService {private String message;public void foo1() {if (true) {this.message = "a";} else {this.message = "b";}}public void foo2() {// 改動this.message的代碼...// ... ...}
}

假設你打算在@Controller里這么調用AccountService :?

accountService.foo1();model.addAttribute(accountService.getMessage());

那么就有線程安全的危急了。


問題原因

在Spring中。bean的默認scope是singleton,也就是說容器中僅僅有一個bean的實例。而在Java Web環境中,webserver會為每個請求創建一個線程來處理它。這樣一來。在@Controller中調用@Service bean的方法就會導致有多個線程在運行@Service方法。比如線程A在運行foo1()方法,線程B在運行foo2()方法。

那么問題來了,多個線程同一時候讀寫message成員變量。就可能讓getMessage()方法返回錯誤的值


解決方法

1. 將@Service bean的scope改為 "request",即:
@Service
@Scope("request")
public class AccountService {private String message;

這樣Spring會為每個請求分別創建一個AccoutService對象,每個線程都有自己的message變量。就不會出錯了。

但壞處是創建@Service bean的開銷往往比較大,會導致程序性能下降。


2. 使用不可變對象(Immuable Object)封裝message變量
定義例如以下類:
class MessageWrapper {private String message;public MessageWrapper(String msg) {this.message = msg;}// 僅僅提供get方法public String getMessage() {return this.message;}
}

AccountService的foo1()方法改動例如以下:
@Service
public class AccountService {public MessageWrapper foo1() {if (true) {return new MessageWrapper("a");} else {return new MessageWrapper("b");}// ... ...}

這樣便能夠完美避免線程安全問題,又不會帶來過多的額外開銷。

轉載于:https://www.cnblogs.com/gcczhongduan/p/5243104.html

本文來自互聯網用戶投稿,該文觀點僅代表作者本人,不代表本站立場。本站僅提供信息存儲空間服務,不擁有所有權,不承擔相關法律責任。
如若轉載,請注明出處:http://www.pswp.cn/news/257606.shtml
繁體地址,請注明出處:http://hk.pswp.cn/news/257606.shtml
英文地址,請注明出處:http://en.pswp.cn/news/257606.shtml

如若內容造成侵權/違法違規/事實不符,請聯系多彩編程網進行投訴反饋email:809451989@qq.com,一經查實,立即刪除!

相關文章

java class 關鍵字_java關鍵字及其作用

一、 關鍵字總覽:訪問控制privateprotectedpublic類,方法和變量修飾符abstractclassextendsfinalimplementsinterfacenativenewstaticstrictfpsynchronizedtransientvolatile程序控制breakcontinuereturndowhileifelseforinstanceofswitchcasedefault錯誤處理trycatchthrowthro…

3.過濾數據 ---SQL

一、使用WHERE子句 SELECT prod_name, prod_price FROM Products WHERE prod_price 3.49; 輸出▼ prod_name prod_price ------------------- ---------- Fish bean bag toy 3.49 Bird bean bag toy 3.49 Rabbit bean bag toy 3.49 分析▼ 這條語句從products表中檢索兩個列&a…

IOS-C語言第8天,Struct (結構體)

轉載于:https://www.cnblogs.com/xiangrongsu/p/4309160.html

Win2D 入門教程 VB 中文版 - 防止內存泄漏

避免內存泄漏 本文從微軟官方文檔翻譯 http://microsoft.github.io/Win2D/html/RefCycles.htm 如果文檔有問題,可以在 https://github.com/Nukepayload2/Win2dDocVB發 Issue,也可以直接回復。 當在托管的 XAML 應用程序中使用 Win2D 控件,需要…

java concurrent 鎖_java并發機制鎖的類型和實現

synchronized 和 volatile,是最基礎的兩個鎖!volatile是輕量級鎖,它在多核處理器開發中保證了共享變量的可見性。即當一個線程修改一個共享變量時,其他線程能夠讀到這個修改的值。它比syncronized使用和成本更低。要說volatile的實…

JAXB和XStream比較

這兩東東本質上是有差別的,JAXB稱為OX binding工具,XStream應該算序列化工具,但OX binding工具也會marshall和unmarshall,所以包含了序列化這一部分。序列化工具不一定需要提供binding的功能。既然都玩序列化,那就簡單…

【起航計劃 011】2015 起航計劃 Android APIDemo的魔鬼步伐 10 App-Activity-Reorder Activities 后退棧 Intent FLAG...

Reorder Activities 示例有四個相關的Activitives: ReorderOnLaunch, ReorderTwo,ReorderThree, ReorderFour。其中ReorderOnLaunch為主Activity,ReorderOnLaunch啟動ReorderTwo ,ReorderTwo啟動 ReorderThree,ReorderThree啟動 ReorderFour。…

java date dateformat_java中Date與DateFormat的格式輸出

一、DateFormatjava.text.DateFormat使用 getDateInstance 來獲取該國家/地區的標準日期格式。另外還提供了一些其他靜態工廠方法。使用 getTimeInstance 可獲取該國家/地區的時間格式。使用 getDateTimeInstance 可獲取日期和時間格式。可以將不同選項傳入這些工廠方法&#x…

spartan6不能直接把時鐘連到IO上

1、問題的提出:spartan6中不允許時鐘信號直接連到IO口上面? 2、解決辦法:ODDR2的使用 ODDR2Primitive: Double Data Rate Output D Flip-Flop with Optional Data Alignment, Clock Enable and Programmable Synchronous or Asynchronous Set…

STL容器及適配器

STL容器 1.序列式容器 : vector,deque,list。 每個元素都有固定的位置(取決于插入的時機和位置,與元素值無關)。 vector 特點: 將一個元素置于一個動態數組中加以管理,可以隨機存取元…

Html5 Canvas斗地主游戲

過完年來公司,沒什么事,主管說研究下html5 游戲,然后主管就給了一個斗地主的demo,隨后我就開始看代碼, 現在我看了html5以及canvas相關知識和斗地主的demo后,自己用demo上的素材試著寫了個斗地主&#xff0…

java流的傳遞方式是_如何在方法中流式傳輸Java List(Varargs)的值?

我有以下方法:public static List getValuesExclusion(A exclusion) {return Arrays.stream(values()).filter(item -> item ! exclusion).collect(Collectors.toList());}//this function returns enum list of A types that has no A typeexclusion現在我想將它…

JAVA作業——JAVA課程的總結及學習計劃

JAVA作業——JAVA課程的總結及學習計劃 NO.1 總結 在上一年的學習中,對JAVA語言比較陌生,英語基礎不好,so學習起來有點困難,對JAVA的一些語法和編程記得比較少。 NO.2 計劃 對過去一年的認真反思之后,我的計劃如下&…

由LintCode問題子集出發,淺析ArrayList的拷貝問題

在做LintCode上的遞歸類題目子集時&#xff0c;我一開始的想法是遞歸到最后一層即單元素時然后開始逐層返回&#xff0c;產生相應的每層的子集并添加到最終的結果中去。于是乎有了以下代碼&#xff1a; public List<List<Integer>> findSolution(int[] nums, int b…

大小端模式詳解

http://www.cnblogs.com/xinsheng/archive/2012/04/18/2455039.html 端模式&#xff08;Endian&#xff09;的這個詞出自Jonathan Swift書寫的《格列佛游記》。這本書根據將雞蛋敲開的方法不同將所有的人分為兩類&#xff0c;從圓頭開始將雞蛋敲開的人被歸為Big Endian&#xf…

.NET 跨平臺服務端資料

OWIN Web API: http://www.asp.net/web-api/overview/hosting-aspnet-web-api/use-owin-to-self-host-web-api 用于寫API的 OWIN SignalR: http://www.dotnetcurry.com/signalr/915/owin-katana-signalr-web-server 用于寫即時通訊的轉載于:https://www.cnblogs.com/Jarvin…

mysql的查詢、子查詢及連接查詢

一、mysql查詢的五種子句 where子句&#xff08;條件查詢&#xff09;&#xff1a;按照“條件表達式”指定的條件進行查詢。 group by子句&#xff08;分組&#xff09;&#xff1a;按照“屬性名”指定的字段進行分組。group by子句通常和count()、sum()等聚合函數一起使用。 h…

BZOJ-1192-鬼谷子的錢袋

描述 鬼谷子非常聰明&#xff0c;正因為這樣&#xff0c;他非常繁忙&#xff0c;經常有各諸侯車的特派員前來向他咨詢時政。有一天&#xff0c;他在咸陽游歷的時候&#xff0c;朋友告訴他在咸陽最大的拍賣行&#xff08;聚寶商行&#xff09;將要舉行一場拍賣會&#xff0c;其中…

lamp 獨立mysql_lamp or lnmp 環境搭建之獨立安裝mysql數據庫

lamp or lnmp 環境搭建,如果mysql 是獨立安裝的則需要授權&#xff1a;單獨一臺服務器獨立安裝mysql安裝后&#xff0c;優化服務器。授權實例如下&#xff1a;創建用戶CREATE USER demo IDENTIFIED BY “passwd123”;授權使用mysql數據庫下面的所有表GRANT ALL PRIVILEGES ON m…

item 24: 區分右值引用和universal引用

本文翻譯自《effective modern C》&#xff0c;由于水平有限&#xff0c;故無法保證翻譯完全正確&#xff0c;歡迎指出錯誤。謝謝&#xff01; 博客已經遷移到這里啦 古人曾說事情的真相會讓你覺得很自在&#xff0c;但是在適當的情況下&#xff0c;一個良好的謊言同樣能解放你…