2011-11-22 20 views
3

我有一個double作爲hashmap中的值,其中的鍵值爲String。如果我單獨更新作爲值添加到散列映射的變量,而不是在散列映射中更新它,則不會反映更新後的值。那是當我使用鍵來獲取值,我得到的值爲0.0而不是更新的值。我無法理解爲什麼會發生這種情況。請在此點亮一下。另外,有沒有其他方式通過更新變量來更新hashmap中的值。我所談論的樣本代碼如下:使用double作爲hashmap中的值的問題

import java.util.HashMap; 
public class TestDouble{ 
    public Double d1 = 0.0; 
    public Double d2 = 0.0; 
    public Double d3 = 0.0; 
    private HashMap<String,Double> hm; 

    public TestDouble(){ 
     hm = new HashMap<String,Double>(); 
     hm.put("D1",d1); 
     hm.put("D2",d2); 
     hm.put("D3",d3); 
    } 

    public void updateD1(double d){ 
     d1 = d; 
    } 

    public void updateD2(double d){ 
     d2 = d; 
    } 

    public void updateD3(double d){ 
     d3 = d; 
    } 

    public Double getValue(String key){ 
     Double val = (Double)hm.get(key); 
     return val; 
    } 

    public static void main(String args[]){ 
     TestDouble td =new TestDouble(); 
     td.updateD1(10.10); 
     td.updateD2(20.20); 
     td.updateD3(30.30); 
     System.out.println("Value of D1 from HashMap = "+td.getValue("D1")+" from actual variable = "+td.d1); 
     System.out.println("Value of D2 from HashMap = "+td.getValue("D2")+" from actual variable = "+td.d2); 
     System.out.println("Value of D3 from HashMap = "+td.getValue("D3")+" from actual variable = "+td.d3); 
    } 
} 

我得到的輸出是:

Value of D1 from HashMap = 0.0 from actual variable = 10.1 
Value of D2 from HashMap = 0.0 from actual variable = 20.2 
Value of D3 from HashMap = 0.0 from actual variable = 30.3 
+0

感謝所有。我想我必須找到另一種方式來做到這一點。再次感謝 – shamshu

回答

7

Double是不可改變的。您無法更新其值。相反,你可以參考的Double

d1另一個實例有一個0d參考:

Double d1 = 0d; 

如果我們做另外一個初始化將引用另一個值:

d1 = 1d; 

在另一方面HashMap是可變的,即其內部狀態可以改變:

Map<String, Double> map = new HashMap<String, Double>(); 
map.put("first", 0d); 
map.put("first", 1d); 
System.out.println("first = " + map.get("first")); 

輸出將是:

first = 1.00 

記住,我們更換了關鍵first關聯的值,它不會被更新。

0

Double是一個與String類似的不可變數據類型。所以當你使用一個變量來幫助爲一個映射設置一個值,然後後者將其設置爲其他值時,兩個Double值是不同的。難怪你爲什麼會得到觀察到的行爲。

1

在Java變量中包含對對象的引用。最初d1和D1的HashMap條目指向同一個對象(因此它們都包含相同的引用)。

當您將變量d1修改爲指向一個新對象時,該變量的值將更改爲對該新對象的引用。此更改僅適用於d1,D1的HashMap條目仍具有原始引用作爲其值,因此仍指向Double 0.00。

1

Java將值傳遞給引用,這意味着您的d1是對值爲0.0的Double實例的引用。將它放入地圖中時,不要將d1放在地圖中,而要放入d1參考的副本(也指向值爲0.0的Double實例)。所以沒有你有兩個引用你的Double,一個來自d1,另一個來自地圖。當您更改d1時,不會更改Double的值,而是將參考d1更改爲指向另一個Double,並且這不會更改存儲在地圖中的參考。

要獲得您想要的效果,您需要存儲一個對象,並將該對象保留在該對象中並更改該對象的值。例如:

import java.util.HashMap; 

public class TestDouble { 

    private static class Holder { 
     Double value = 0.0; 
    } 

    private HashMap<String,Holder> hm = new HashMap<String,Holder>();; 

    private Holder d1 = new Holder(); 

    public TestDouble(){ 
     hm = new HashMap<String,Holder>(); 
     hm.put("D1",d1); 
    } 

    public void updateD1(double d){ 
     d1.value = d; 
    } 

    public Double getValue(String key) { 
     return hm.get(key).value; 
    } 

    public static void main(String args[]){ 
     TestDouble td =new TestDouble(); 
     System.out.println("Value of D1 from HashMap = "+td.getValue("D1")+" from actual variable = "+td.d1.value); 
     td.updateD1(10.10); 
     System.out.println("Value of D1 from HashMap = "+td.getValue("D1")+" from actual variable = "+td.d1.value); 
    } 
} 
+0

感謝您的意見。我已經做了類似於你所建議的事情。只有我在靜態持有者類中使用了原始double。我認爲這應該沒問題。否則請告訴我。再次感謝。 – shamshu

+0

這應該沒問題,我只是希望儘可能使示例與原始代碼儘可能接近。 –

+0

再次感謝@Roger – shamshu