我對Java HashMap有一些奇怪的和意想不到的行爲,僅僅用於測試的一部分代碼。我可以有一個非空的hashmap,其中沒有任何鍵嗎?
要儘量將其存儲在會議上,我使用if{}else{}
聲明,但我發現自己與我的應用程序錯誤之前一個唯一的ID設置爲一個對象。爲測試目的,產生
的ID,因爲目前沒有數據庫實際存儲的數據,其被存儲在會話在其間。
這裏是我的代碼片段:
...
HttpSession session = request.getSession();
Map<Integer, Booking> bookings = (HashMap<Integer, Booking>) session.getAttribute(SESSION_BOOKINGS);
// Generates ID
if (bookings == null)
{
bookings= new HashMap<Integer, Booking>();
identificator = 1;
}
else
{
Object[] arrayKeys = (Object[]) bookings.keySet().toArray();
Arrays.sort(arrayKeys);
identificator = (Integer) arrayKeys[arrayKeys.length - 1] + 1;
}
...
//... The rest is setting the ID to the current worked on booking,
//... putting the ID/booking pair in the bookings map
//... and storing the map in session, which worked fine
刪除預訂的地圖時,地圖僅包含一個錯誤後走了過來。當我試圖註冊後,多了一個,我得到了下面的錯誤原因java.lang.ArrayIndexOutOfBoundsException: -1
,並鏈接到我的else
聲明的最後一行的跟蹤誤差:identificator = (Integer) arrayKeys[arrayKeys.length - 1] + 1;
所以:
arrayKeys.length -1 == -1 // true
- 這意味着
arrayKeys.length == 0 // true
這又意味着從
Map<Integer,Booking> bookings
所述keySet()
是空但測試沒有進入
if
聲明
在另一方面,在一個全新的會話(或重新啓動瀏覽器或重新登錄並在後),測試沒有進入if語句作爲預期。
經過測試,我將自己的狀況從(bookings==null)
改爲(bookings==null || bookings.isEmpty())
。
進一步的測試表明,只使用(bookings.isEmpty()
在新會話中註冊預訂時導致NPE。
所以我想知道是否有可能一個地圖是非空的沒有任何價值(顯然,是的,但我也問自己是如何)以及它怎麼沒有返回後爲null它完全被清空了?
儘管我得到它在new
聲明後爲空,怎麼會在session.getAttribute()
調用之後呢?這似乎很明顯,因爲沒有地圖存儲在會話中,但同時它似乎很奇怪,因爲沒有new
聲明。