简体   繁体   English

Java - 从HashMap中检索对象

[英]Java - Retrieving objects from HashMap

I have a problem when retrieving values from a hashmap. 从hashmap中检索值时出现问题。 The hashmap is declared as follows: hashmap声明如下:

HashMap<TRpair,A> aTable = new HashMap<TRpair,A>();

I then put 112 values into the map as follows: 然后我将112个值放入地图中,如下所示:

aTable.put(new TRpair(new T(<value>),new Integer(<value>)),new Ai());

where Ai is any one of 4 subclasses that extend A. 其中Ai是扩展A的4个子类中的任何一个。

I then proceed to check what values are in the map, as follows: 然后我继续检查地图中的值,如下所示:

int i = 0;
for (Map.Entry<TRpair,A> entry : aTable.entrySet()) {
    System.out.println(entry.getKey().toString() + " " + entry.getValue().toString());
    System.out.println(entry.getKey().equals(new TRpair(new T("!"),new Integer(10))));
    i++;
}

i holds the value 112 at the end, as one would expect and the equality test prints true for exactly one entry, as expected. 正如人们所预料的那样,我在结尾处保持值112,并且正如预期的那样,对于一个条目,相等性测试打印为真。

However, when I do 但是,当我这样做的时候

System.out.println(aTable.get(new TRpair(new T("!"), new Integer(10))));

null is output, despite the above code snippet confirming that there is indeed one entry in the map with exactly this key. 尽管上面的代码片段确认地图中确实存在一个恰好具有此键的条目,但仍输出null。

If it helps, the class TRpair is declared as follows: 如果有帮助,则TRpair类声明如下:

public class TRpair {
    private final T t;
    private final Integer r;

    protected TRpair(Integer r1, T t1) {
        terminal = t1;
        row = r1;
    }

    protected TRpair(T t1, Integer r1) {
        t = t1;
        r = r1;
    }

    @Override
    public boolean equals(Object o) {
        TRpair p = (TRpair)o;
        return (p.t.equals(t)) && (p.r.equals(r));
    }

    @Override
    public String toString() {
        StringBuilder sbldr = new StringBuilder();
        sbldr.append("(");
        sbldr.append(t.toString());
        sbldr.append(",");
        sbldr.append(r.toString());
        sbldr.append(")");
        return sbldr.toString();
    }
}

the equals() and toString() methods in each of the Ai (extending A) and in the T class are overridden similarly and appear to behave as expected. Ai(扩展A)和T类中的equals()和toString()方法被类似地重写并且看起来表现得如预期的那样。

Why is the value output from the hashmap aTable null, when previously it has been confirmed that the value for the corresponding key is indeed in the map? 为什么从hashmap aTable输出的值为null,之前已经确认相应键的值确实在地图中?

With many thanks, 非常感谢,

Froskoy. Froskoy。

The keys/elements for a Hash collection but override hashCode() if euqals is overridden. 哈希集合的键/元素,但如果覆盖了euqals则覆盖hashCode()。

You could use. 你可以用。

public int hashCode() {
    return t.hashCode() * 31 ^ r.hashCode();
}

BTW: It appears from your code that Integer r cannot be null in which case using int r makes more sense. BTW:从你的代码看来, Integer r不能为null在这种情况下使用int r更有意义。

From Object.equals() 来自Object.equals()

Note that it is generally necessary to override the hashCode method whenever this method is overridden, so as to maintain the general contract for the hashCode method, which states that equal objects must have equal hash codes. 请注意,通常需要在重写此方法时覆盖hashCode方法,以便维护hashCode方法的常规协定,该方法声明相等的对象必须具有相等的哈希代码。

IIRC hashmap looks up by hashCode() and not by equality, and since you did not implemented hashcode you use default implementation which is consistent with object pointer equality - you need to implement proper hashcode function which takes into account "T" parameter as well as integer (or not) IIRC hashmap通过hashCode()而不是相等来查找,并且由于你没有实现hashcode,你使用与对象指针相等一致的默认实现 - 你需要实现适当的hashcode函数,它考虑了“T”参数以及整数(或不)

It is good practice that hashCode() and equals() are consistent, but not structly necessary if you know what you are doing. 好的做法是hashCode()和equals()是一致的,但如果你知道自己在做什么,则不需要在结构上。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM