2012-05-23 49 views
0

我有一个程序需要合并两个HashMap。 hashmaps的密钥是String,值是Integer。合并的特殊情况是,如果密钥已存在于字典中,则需要将Integer添加到现有值中,而不是将其替换。这里是我到目前为止的代码投掷NullPointerException在Java中合并2个HashMaps

public void addDictionary(HashMap<String, Integer> incomingDictionary) { 
     for (String key : incomingDictionary.keySet()) { 
      if (totalDictionary.containsKey(key)) { 
       Integer newValue = incomingDictionary.get(key) + totalDictionary.get(key); 
       totalDictionary.put(key, newValue); 
      } else { 
       totalDictionary.put(key, incomingDictionary.get(key)); 
      } 
     } 
    } 
+0

NPE被抛出的线是什么? – BenCole

+0

你是否初始化了'totalDictionary'字段? – BenCole

+0

totalDictionary已声明,但未初始化为包装此函数的类中较早的私有成员数据。 Eclipse显示在for循环处引发的异常。 – SmashCode

回答

1

如果你的代码不能保证incomingDictionary将达到此方法前必须初始化,你必须做一个空检查,没有出路

public void addDictionary(HashMap<String, Integer> incomingDictionary) { 
    if (incomingDictionary == null) { 
     return; // or throw runtime exception 
    } 
    if (totalDictionary == null) { 
     return;// or throw runtime exception 
    } 
    if (totalDictionary.isEmpty()) { 
     totalDictionary.putAll(incomingDictionary); 
    } else { 
     for (Entry<String, Integer> incomingIter : incomingDictionary.entrySet()) { 
      String incomingKey = incomingIter.getKey(); 
      Integer incomingValue = incomingIter.getValue(); 
      Integer totalValue = totalDictionary.get(incomingKey); 
      // If total dictionary contains null for the incoming key it is 
      // as good as replacing it with incoming value. 
      Integer sum = (totalValue == null ? 
              incomingValue : incomingValue == null ? 
                totalValue : totalValue + incomingValue 
         ); 
      totalDictionary.put(incomingKey, sum); 
     } 
    } 
} 

考虑的HashMap允许空值,如在你的代码另一个地方是容易NPE是

Integer newValue = incomingDictionary.get(key) + totalDictionary.get(key); 

如果这两种为n你会得到NPE。

+0

if(totalDictionary.isEmpty())then totalDictionary.putAll(incomingDictionary)else if for循环呢? – SmashCode

+0

如果incomingDictionary为null,那么putAll将抛出NullPointerException – mprabhat

+0

@SmashCode更新了我的答案 – mprabhat

0

考虑到totalDictionary被正确初始化,在:

Integer newValue = incomingDictionary.get(key) + totalDictionary.get(key); 

totalDictionary.get(key)无法返回null
也许你需要之前,这样的补充了一句:

if(totalDictionary.get(key) == null) 
    totalDictionary.put(key, 0); 
2

您可能有一个未初始化的字典。 以下是一种解决方案:

public void addDictionary(HashMap<String, Integer> incomingDictionary) { 
    if (incomingDictionary == null) { 
     throw new IllegalArgumentException("incomingDictionary cannot be null."); 
    } 
    if (totalDictionary == null) { 
     throw new IllegalArgumentException("totalDictionary cannot be null."); 
     // or another solution: 
     // totalDictionary = new HashMap<String, Integer>(); 
     // totalDictionary.putAll(incomingDictionary); 
     // return; 
    } 

    for (Map.Entry<String, Integer> entry : incomingDictionary.entrySet()) { 
     Integer oldValue = totalDictionary.get(entry.getKey()); 
     if (oldValue != null){ 
      // here entry.getValue() could be null! 
      // Never put a null value in your Map, or add a test here 
      Integer newValue = entry.getValue() + oldValue; 
      totalDictionary.put(entry.getKey(), newValue); 
     } else { 
      totalDictionary.put(entry.getKey(), entry.getValue()); 
     } 
    } 
} 
+0

+1用于抛出异常,而不是仅仅以失败告终! – BenCole

+1

如果entry.getValue()返回null,再次NPE – mprabhat

+0

确实!但我认为这是他的责任,永远不会把'null'作为一个值的地图......但我会根据您的评论编辑我的帖子。 –