用两个键映射值?

时间:2012-05-28 16:36:27

标签: java data-structures map arraylist linked-list

我想创建一个有两个键的地图:

map.put (key1,key2,value1);// Insert into map
map.get(key1,key2); // return value1

我正在研究 multikeyMap ,但我不知道我将如何做到这一点

7 个答案:

答案 0 :(得分:10)

听起来你只想要一个由两个值创建的密钥。您可能会发现这两个值无论如何都应自然地封装到另一个类型中 - 或者您可以创建Key2<K1, K2>类型。 (这里的命名允许Key3Key4等等。我不鼓励你走得太远。)

对于介于两者之间的东西,你可以在类中创建一个真正需要的私有静态类(如果它只是一个内部实现细节)。如果它不是一个自然的封装(例如,它类似于“名称和人口”,在这个特定的场景之外没有意义)那么它在保留有意义的属性名称方面会很好,但不会公开它。

在任何这些情况下,您最终会得到一个新类型,其中包含两个最终变量,这些变量在构造函数中初始化,并且对equalshashCode都有贡献。例如:

public final class Key2<K1, K2> {
    private final K1 part1;
    private final K2 part2;

    public Key2(K1 part1, K2 part2) {
        this.part1 = part1;
        this.part2 = part2;
    }

    @Override public boolean equals(Object other) {
        if (!(other instanceof Key2)) {
            return false;
        }
        // Can't find out the type arguments, unfortunately
        Key2 rawOther = (Key2) other;
        // TODO: Handle nullity
        return part1.equals(rawOther.part1) &&
            part2.equals(rawOther.part2);
    }

    @Override public int hashCode() {
        // TODO: Handle nullity
        int hash = 23;
        hash = hash * 31 + part1.hashCode();
        hash = hash * 31 + part2.hashCode();
        return hash;
    }

    // TODO: Consider overriding toString and providing accessors.
}

更多特定于情境的类型会稍微简单一些,因为它们不是通用的 - 特别是这意味着您不需要担心类型参数,并且可以为变量赋予更好的名称。

答案 1 :(得分:10)

怎么样

class Key{
 private final String key1;
 private final String key2;
//accessors + hashcode + equals()
}

Map<Key, Value> map

答案 2 :(得分:2)

您可以考虑使用Guava的Table实现之一。来自文档:

  

关联一组有序键的集合,称为行键   和列键,具有单个值。表格可能很稀疏,有   只有一小部分行键/列密钥对拥有一个   相应的价值。

答案 3 :(得分:2)

如果您可以使用外部库,Guava提供的内容为Table<R, C, V>,将两个密钥分别称为“行”和“列”。 (披露:我向Guava捐款。)

答案 4 :(得分:1)

为什么不将key键映射并连接key1 + key2

答案 5 :(得分:1)

如果你总是希望通过key1和key2一起访问,你可以将它们作为键一起连接到分隔符并使用法线贴图。

答案 6 :(得分:1)

遗憾的是,Java不支持语言级别的元组,因此你必须选择临时结构,就像这里的一些答案所示。这导致了大量的样板和代码重复。

Functional Java拥有对元组的库支持。适合该法案的课程是P2。该名称的意思是“具有2个元素的产品”。 (Product只是复合类型的代数术语。)库支持最多8个元素的元组。 P{n}类覆盖所有必要的方法

有一个名为P的类,它提供了一个静态工厂方法p来构造元组。

<强>用法:

import fj.P2;
import fj.Ord;
import fj.data.TreeMap;

import static fj.Ord.*;
import static fj.P.*;

TreeMap<P2<Integer, String>, String> m = 
  TreeMap.<P2<Integer, String>, String>empty(p2Ord(intOrd, stringOrd)).
  set(p(1, "2"), "onetwo").
  set(p(5, "3"), "fivethree");