1. 程式人生 > >並發入庫面臨重復數據的問題

並發入庫面臨重復數據的問題

方案 ice 服務 數據庫 關註 處理 user 進行 數據

並發入庫面臨重復數據的問題

以User類為例,當添加一個用戶時,首先會去判斷用戶是否已經存在(即username是否已經在數據庫中了),如果沒有,則insert一條用戶數據,如果有,則提示用戶名已存在。

將這個操作看作函數:UserService.saveUser(User user),有3個步驟:

private int saveUser(User user) {
  if
(1.username不存在) {     // 2.入庫;   } else {     // 3.提示用戶名已存在;   }
}

這個saveUser函數實際上是線程不安全的,假設兩個線程A和線程B,兩個線程同時進行了判斷(步驟1

),發現username不存在,那麽就會導致user表中插入了兩個username一樣的數據(步驟2)。

解決方案一

最直接的,通過添加synchronized關鍵字,將方法變成同步方法

優點:簡單直接

缺點:性能問題;後期的維護成本較高;最終要的,當服務部署在多臺設備時不起作用


解決方案二

在數據庫的user表中,將username字段設為唯一索引,這樣當插入重復數據時,數據庫會拋出異常,無法入庫,可以通過異常處理的方式來處理

優點:從比較根源的數據庫層面解決了問題,適用與分布式環境

缺點:需要關註異常處理

並發入庫面臨重復數據的問題