2014-05-14 27 views
0

我給用戶編輯我的數據庫中的文件的選項。但我不想同時對同一個文件進行多次編輯,因此爲了防止這種情況,我在服務器端使用了一個靜態鏈接列表。當客戶端發送請求更新文件到服務器時,LinkedList.contain(filename)將檢查文件名是否存在於列表中。如果它不存在,則反而會加重它並允許更新,否則只會返回響應。發生了錯誤。該代碼是這樣的:在服務器端安全使用靜態LinkedList?

public class UpdateFileServlet extends HttpServlet{ 

    private static List<String> List= new LinkedList<String>(); 
     @Override 
     public void doPost(HttpServletRequest req, HttpServletResponse res) 
        throws ServletException, IOException { 
      String file=req.getHeader("FileName"); 
      if(List.contains(file)){ 
       res.getWriter().write("Error"); 
       res.flushBuffer(); 
       return; 
      } 
      List.add(file); 
      try{ 
      //do the file update; 

       List.remove(file); 

      }catch (Exception e1) { 
       List.remove(file); 
       e1.printStackTrace(); 
      } 
     } 
    } 
} 

我還添加try/catch語句,這樣即使發生任何異常,文件名也會從列表中刪除。否則該文件將永遠不可編輯。我知道這不是最好的方法,但我想知道是否有任何條件,其中鏈表將失敗或者是否有任何更好的解決方案的問題?

在此先感謝您的任何幫助或建議...

+1

'LinkedList'本身不是線程安全的(不同步)。你可能想看看像這樣的問題(http://stackoverflow.com/questions/3362018/is-linkedlist-thread-safe-when-im-accessing-it-with-offer-and-poll-專門)一個確保你沒事。 Servlets *應該是無狀態的,所以你可以考慮使用數據庫。 – Baz

+1

請注意:變量應以小寫字母開頭;) – Baz

+0

這並不安全,假設您有兩個用戶與您的系統同時工作,並且都想同時訪問同一個文件。 在將文件添加到列表之前,它們都通過檢查'if(List.contains(file))'。 – user902383

回答

1

幾點。

  1. LinkedList不是線程安全的。搜索時間也是線性的。你可能要考慮ConcurrentHashMap。而不是做list.add()你做ConcurrentMap.putIfAbsent()並檢查返回的值。

  2. 人們可能會通過不同的途徑,例如絕對VS相對路徑都指向相同的實際文件。所以最好在你的持有結構中使用File對象而不是字符串。

  3. 我想你想要做list.remove(file),無論更新是否成功。所以你需要把它放到finally區塊。

+0

感謝您的回答...... jst一個人認爲......如果他們同時到達,請確保ConcurrentMap.putIfAbsent()不會接受兩個請求。 – user3335722

+0

ConcurrentMap.putIfAbsent()可能一起接收2個請求;但是實施例如ConcurrentHashMap具有內部鎖。在ConcurrentHashMap的情況下,它在內部哈希表中的每個「單元」上都有一個ReadWriteLock。通過這樣做,它會比在整個地圖結構上使用同步或ReadWriteLock獲得更好的性能。所以,即使您一起有兩個電話,只有一個電話會返回true。 –

+0

謝謝Alex!真的很感謝幫助... – user3335722