Java 具有空键和空值的 HashMap

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/25932730/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me): StackOverFlow

提示:将鼠标放在中文语句上可以显示对应的英文。显示中英文
时间:2020-08-11 01:31:47  来源:igfitidea点击:

HashMap with Null Key and Null Value

javacollectionsnullhashmaphashcode

提问by Nizam

Consider the following Code :

考虑以下代码:

import java.util.*;

class Employee {

    String name;

    public Employee(String nm) {
        this.name=nm;
    }
}

public class HashMapKeyNullValue {

    Employee e1;

    public void display(){

        Employee e2=null;
        Map map=new HashMap();

        map.put(e2, "25");
        System.out.println("Getting the Value When e2 is set as KEY");
        System.out.println("e2 : "+map.get(e2));
        System.out.println("e1 : "+map.get(e1));
        System.out.println("null : "+map.get(null));

        map.put(e1, "");
        System.out.println("Getting the Value when e1 is set as KEY");
        System.out.println("e2 : "+map.get(e2));
        System.out.println("e1 : "+map.get(e1));
        System.out.println("null : "+map.get(null));

        map.put(null, null);   // null as key and null as value
        System.out.println("Getting the Value when setting null as KEY and null as value");
        System.out.println("e2 : "+map.get(e2));
        System.out.println("e1 : "+map.get(e1));
        System.out.println("null : "+map.get(null));

        map.put(null, "30");
        System.out.println("Getting the Value when setting only null as KEY");
        System.out.println("e2 : "+map.get(e2));
        System.out.println("e1 : "+map.get(e1));
        System.out.println("null : "+map.get(null));
    }

    public static void main(String[] args) {

        new HashMapKeyNullValue().display();

    }
}

The Output of program is :

程序的输出是:

Getting the Value When e2 is set as KEY
e2 : 25
e1 : 25
null : 25
Getting the Value when e1 is set as KEY
e2 : 
e1 : 
null : 
Getting the Value when setting null as KEY and null as value
e2 : null
e1 : null
null : null
Getting the Value when setting only null as KEY
e2 : 30
e1 : 30
null : 30

Here how e1, e2, and nullas keys are related to each other. Is all three are assigned to same hashcode ? If yes, WHY ?

这里如何e1, e2, and null作为键相互关联。所有三个都分配给相同的哈希码吗?如果是,为什么?

Since all three seems to be look different the change in one value changes the other. Does it mean that only one entry for key is being made into HashMapeither e1, e2, or nullbeacause all treated to be like the same key.

由于所有三个看起来都不同,因此一个值的变化会改变另一个。这是否意味着只有一个 key 条目被输入HashMap到任一中,e1, e2, or null因为所有条目都被视为同一个 key。

采纳答案by Sandeep Vaid

HashMapdoes not call hashcode when nullis passed as key and null Key is handled as special case.

HashMapnull作为 key 传递时不调用 hashcode并且 null Key 作为特殊情况处理。

Put Method

放置方法

HashMapputs nullkey in bucket 0and maps nullas key to passed value. HashMap does it by linked list data structure. HashMap uses linked list data structure internally.

HashMap键放入桶0并将值映射为传递值的键。HashMap 通过链表数据结构来实现。HashMap 内部使用链表数据结构。

Linked list data structure used by HashMap(a static class in HashMap.java)

HashMap( 中的静态类HashMap.java)使用的链表数据结构

static class Entry<K,V> implements Map.Entry<K,V> {
        final K key;
        V value;
        Entry<K,V> next;
        final int hash;
}

In Entry class the Kis set to nulland value mapped to value passed in put method.

在 Entry 类中,K设置为null,并将值映射到 put 方法中传递的值。

Get Method

获取方法

While in Hashmapget method the checks if key is passed as null. Search Value for nullkey in bucket 0.

Hashmapget 方法中,检查 key 是否作为null传递。存储桶0中空键的搜索值。

Hence there can only be one null key in one hashmapobject.

因此只能有一个空键合二为一 hashmap目的。

回答by dunni

A HashMap can only store one value per key. If you want to store more values, you have to use a MultivalueHashMap (Google Guava and Apache Commons Collections contain implementations of such a map).

HashMap 每个键只能存储一个值。如果要存储更多值,则必须使用 MultivalueHashMap(Google Guava 和 Apache Commons Collections 包含此类映射的实现)。

e1 and e2 have the value null, since you don't assign any object to them. So if you use those variables, the key of that map entry is also null, which leads to your result. Null doesn't have any hashcode, but is tolerated as key in the HashMap (there are other Map implementations which don't allow Null as key).

e1 和 e2 的值为 null,因为您没有为它们分配任何对象。因此,如果您使用这些变量,则该映射条目的键也是 null,这会导致您的结果。Null 没有任何哈希码,但可以作为 HashMap 中的键被容忍(还有其他 Map 实现不允许 Null 作为键)。

回答by Mykola Evpak

When you put NULL to HashMap there is special check if you are trying to put NULL as key (called putForNullKey()). It is special case and works not like you are trying to put some object which is not null, and as you may see it even doesn't go to hash calculation.

当您将 NULL 放入 HashMap 时,如果您尝试将 NULL 作为键(称为putForNullKey()),则会进行特殊检查。这是特殊情况,不像您试图放置一些非空的对象那样工作,而且您可能会看到它甚至不进行哈希计算。

public V put(K key, V value) {
    if (table == EMPTY_TABLE) {
        inflateTable(threshold);
    }
    if (key == null)
        return putForNullKey(value);
    int hash = hash(key);
    int i = indexFor(hash, table.length);
    for (Entry<K,V> e = table[i]; e != null; e = e.next) {
        Object k;
        if (e.hash == hash && ((k = e.key) == key || key.equals(k))) {
            V oldValue = e.value;
            e.value = value;
            e.recordAccess(this);
            return oldValue;
        }
    }

    modCount++;
    addEntry(hash, key, value, i);
    return null;
}

private V putForNullKey(V value) {
    for (Entry<K,V> e = table[0]; e != null; e = e.next) {
        if (e.key == null) {
            V oldValue = e.value;
            e.value = value;
            e.recordAccess(this);
            return oldValue;
        }
    }
    modCount++;
    addEntry(0, null, value, 0);
    return null;
}

回答by Kamil K?ys

If you pass nullas map key, it will go to 0 bucket. All values of null key will go there. That is why it returns same value, cause all keys you are providing are nulland are in the same bucket of your HashMap.

如果您null作为地图键传递,它将转到0 bucket. 空键的所有值都会去那里。这就是为什么它返回相同的值,因为你提供的所有键null都在你的 HashMap 的同一个桶中。

回答by Ravi Soni

Incase of nullkey , Hashmap implementation consider it as special case and doesnot call hashCode method instead it stores Entry object to 0 bucket location.

如果出现键,Hashmap 实现将其视为特殊情况,不会调用 hashCode 方法,而是将 Entry 对象存储到 0 存储桶位置。