开发者

Entries in a HashMap being overwritten by completely different keys?

开发者 https://www.devze.com 2023-01-11 06:24 出处:网络
I have a Java HashMap used to store some basic string values: Map<String, String> map = new HashMap<String, String>();

I have a Java HashMap used to store some basic string values:

Map<String, String> map = new HashMap<String, String>();
map.put("Id", task.getStorageId());
map.put("Name", task.getName());
map.put("Description", task.getDescription());

Under one usage, the Id entry is overwitten by the Description entry, everytime without fail. I have watched it in the debugger - Id is inserted fine, Name inserted fine, then when Descroption is inserted, it overwrites the Id entry. Using exactly the same code and keys in another p开发者_JAVA百科art of the application it works with no problems. Totally confused. What is going on here?

Edit

Perhaps I should have mentioned (though it didn't seem relevant), this is happening on Android, not in a JVM. Could that be the issue? I also found it hard to believe but the chunk of code is as simple as the snippet provided. I will try to bundle an Android app that demonstrates it and post somewhere.


It is likely that the entry you are not seeing is there, look at the modCount for the table and you should see the proper number of entries. This means that a hash collision has occurred. Basically 2 keys got hashed into the same bucket in the table. If you look at the bucket that had the original key it has a next field, which is a pointer to the other entry that you think you have lost.


That should in no way be happening. The HashMap uses a key's hashCode() method to index the Map's entries. Since

"Id".hashCode() == "Description".hashCode()

is false (yes, I just tested it for sanity), the put(String, String) operations are not interfering. Do some more inspection and make sure your code is really the same as what you posted above.


Maybe the code you debug and the sources you use are not in sync? Maybe you have changed your sources but havn't compiled correctly? Perhaps you have a jar with an old version of your softwar eon your classpath?


Not happening to me:

import java.util.Map;
import java.util.HashMap;

public class MapDemo
{
   public static void main(String[] args)
   {
      Map<String, String> map = new HashMap<String, String>();
      map.put("Id", "task.getStorageId()");
      map.put("Name", "task.getName()");
      map.put("Description", "task.getDescription()");

      System.out.println("map: " + map);
   }
}

Here's the output:

com.intellij.rt.execution.application.AppMain MapDemo
map: {Name=task.getName(), Description=task.getDescription(), Id=task.getStorageId()}

Process finished with exit code 0


I had the same experience and in debugging it looked like an entry is overwritten by a completely different entry. When i tried to retrieve the value it returned null.

But it was because, when retrieving I had used simplecase value as key. When used the exact format, value was returning properly.

eg:

  map.put("A", "value1");
  map.put("B", "value2");
  map.put("C", "value3");

  map.get(a) --> null
  map.get(A) --> value1
0

精彩评论

暂无评论...
验证码 换一张
取 消