HashMap在同一个键下有多个值

新手上路,请多包涵

我们是否可以实现一个键和两个值的 HashMap。就像HashMap一样?

请帮助我,同时告诉(如果没有办法)任何其他方式来实现以一个为键的三个值的存储?

原文由 vidhya 发布,翻译遵循 CC BY-SA 4.0 许可协议

阅读 848
2 个回答

你可以:

  1. 使用以列表为值的地图。 Map<KeyType, List<ValueType>>
  2. 创建一个新的包装器类并将此包装器的实例放置在地图中。 Map<KeyType, WrapperType>
  3. 使用类元组(节省创建大量包装器)。 Map<KeyType, Tuple<Value1Type, Value2Type>>
  4. 并排使用多个地图。

例子

1. 以列表为值的映射

// create our map
Map<String, List<Person>> peopleByForename = new HashMap<>();

// populate it
List<Person> people = new ArrayList<>();
people.add(new Person("Bob Smith"));
people.add(new Person("Bob Jones"));
peopleByForename.put("Bob", people);

// read from it
List<Person> bobs = peopleByForename["Bob"];
Person bob1 = bobs[0];
Person bob2 = bobs[1];

这种方法的缺点是列表并不完全绑定到两个值。

2.使用包装类

// define our wrapper
class Wrapper {
    public Wrapper(Person person1, Person person2) {
       this.person1 = person1;
       this.person2 = person2;
    }

    public Person getPerson1() { return this.person1; }
    public Person getPerson2() { return this.person2; }

    private Person person1;
    private Person person2;
}

// create our map
Map<String, Wrapper> peopleByForename = new HashMap<>();

// populate it
peopleByForename.put("Bob", new Wrapper(new Person("Bob Smith"),
                                        new Person("Bob Jones"));

// read from it
Wrapper bobs = peopleByForename.get("Bob");
Person bob1 = bobs.getPerson1();
Person bob2 = bobs.getPerson2();

这种方法的缺点是您必须为所有这些非常简单的容器类编写大量样板代码。

3. 使用元组

// you'll have to write or download a Tuple class in Java, (.NET ships with one)

// create our map
Map<String, Tuple2<Person, Person> peopleByForename = new HashMap<>();

// populate it
peopleByForename.put("Bob", new Tuple2(new Person("Bob Smith",
                                       new Person("Bob Jones"));

// read from it
Tuple<Person, Person> bobs = peopleByForename["Bob"];
Person bob1 = bobs.Item1;
Person bob2 = bobs.Item2;

这是我认为最好的解决方案。

4.多张地图

// create our maps
Map<String, Person> firstPersonByForename = new HashMap<>();
Map<String, Person> secondPersonByForename = new HashMap<>();

// populate them
firstPersonByForename.put("Bob", new Person("Bob Smith"));
secondPersonByForename.put("Bob", new Person("Bob Jones"));

// read from them
Person bob1 = firstPersonByForename["Bob"];
Person bob2 = secondPersonByForename["Bob"];

此解决方案的缺点是这两个地图相关性并不明显,程序错误可能会导致两个地图不同步。

原文由 Paul Ruane 发布,翻译遵循 CC BY-SA 4.0 许可协议

不,不仅仅是 HashMap 。您基本上需要一个 HashMap 从键到值集合。

If you’re happy to use external libraries, Guava has exactly this concept in Multimap with implementations such as ArrayListMultimap , HashMultimap , LinkedHashMultimap 等等

Multimap<String, Integer> nameToNumbers = HashMultimap.create();

System.out.println(nameToNumbers.put("Ann", 5)); // true
System.out.println(nameToNumbers.put("Ann", 5)); // false
nameToNumbers.put("Ann", 6);
nameToNumbers.put("Sam", 7);

System.out.println(nameToNumbers.size()); // 3
System.out.println(nameToNumbers.keySet().size()); // 2

原文由 Jon Skeet 发布,翻译遵循 CC BY-SA 4.0 许可协议

撰写回答
你尚未登录,登录后可以
  • 和开发者交流问题的细节
  • 关注并接收问题和回答的更新提醒
  • 参与内容的编辑和改进,让解决方法与时俱进
推荐问题