Java-从HashMap单键多值获取键(反向映射)

Java-从HashMap单键多值获取键(反向映射),java,data-structures,Java,Data Structures,我有一个HashMap定义如下: if(ArrayListBar.contains(bar)) { return Foo; } else { return null; } Map=newhashmap() 我正在尝试使用栏对Hashmap进行反向搜索,以获得Foo 我想做这样的事情: if(ArrayListBar.contains(bar)) { return Foo; } else { return null; } 这在HashMap中是可以实现的,还是有

我有一个HashMap定义如下:

if(ArrayListBar.contains(bar)) {
    return Foo;
} else {
    return null;
}
Map=newhashmap()

我正在尝试使用
栏对Hashmap进行反向搜索,以获得
Foo

我想做这样的事情:

if(ArrayListBar.contains(bar)) {
    return Foo;
} else {
    return null;
}

这在HashMap中是可以实现的,还是有更好的方法不用HashMap来处理这个问题?

您可以通过Map迭代来实现

private Foo getKeyByValue(Map<Foo, List<Bar>> map, Bar bar){
    for (Map.Entry<Foo, List<Bar>> entry : map.entrySet()){
        if (entry.getValue().contains(bar)){
            return entry.getKey();
        }
    } 
  return null;
}
private Foo getKeyByValue(地图地图、条形图){
对于(Map.Entry:Map.entrySet()){
if(entry.getValue()包含(bar)){
return entry.getKey();
}
} 
返回null;
}
对映射上的每个条目进行迭代,当数组列表包含输入的条值时,返回键

请注意,您的Bar类应该实现equals方法,因此如果列表中的条与方法输入中的条是不同的对象,则可以计算
entry.getValue().contains(Bar)


更新:添加了在找不到映射元素时缺少的
返回null
语句。

您可以通过映射迭代来完成

private Foo getKeyByValue(Map<Foo, List<Bar>> map, Bar bar){
    for (Map.Entry<Foo, List<Bar>> entry : map.entrySet()){
        if (entry.getValue().contains(bar)){
            return entry.getKey();
        }
    } 
  return null;
}
private Foo getKeyByValue(地图地图、条形图){
对于(Map.Entry:Map.entrySet()){
if(entry.getValue()包含(bar)){
return entry.getKey();
}
} 
返回null;
}
对映射上的每个条目进行迭代,当数组列表包含输入的条值时,返回键

请注意,您的Bar类应该实现equals方法,因此如果列表中的条与方法输入中的条是不同的对象,则可以计算
entry.getValue().contains(Bar)


更新:添加了在未找到映射元素时缺少的
返回null
语句。

在不同的情况下,最佳方法可能会有所不同

可以通过迭代映射并检查每个条目的列表是否包含该值来实现。但只有当地图不太大,列表不太大,或者不是太大,或者排序不好时,这才行

但是如果地图的大小很大或者列表很大并且没有排序,并且需要进行多次查找,那么最好创建一个反向地图。 在这种情况下,您必须确保正确实现了Bar的hashkey和equals方法。 如果相同的值(条)可以位于不同键(Foo)的多个列表中,则反向映射可能还需要一个值列表:map>

根据具体情况,可以在构建原始映射时创建反向映射,也可以在执行第一次查找时创建反向映射,并将其缓存以在以后的查找中重用。
当涉及到线程安全性时,最好在创建原始映射时创建它,因为在这种情况下,您不需要担心查找方法的线程安全性,这是在第一次查找期间创建反向映射时出现的问题。

在不同的情况下,最佳方法可能会有所不同

可以通过迭代映射并检查每个条目的列表是否包含该值来实现。但只有当地图不太大,列表不太大,或者不是太大,或者排序不好时,这才行

但是如果地图的大小很大或者列表很大并且没有排序,并且需要进行多次查找,那么最好创建一个反向地图。 在这种情况下,您必须确保正确实现了Bar的hashkey和equals方法。 如果相同的值(条)可以位于不同键(Foo)的多个列表中,则反向映射可能还需要一个值列表:map>

根据具体情况,可以在构建原始映射时创建反向映射,也可以在执行第一次查找时创建反向映射,并将其缓存以在以后的查找中重用。
当涉及到线程安全时,最好在创建原始映射时创建它,因为在这种情况下,您不需要担心查找方法的线程安全,这在第一次查找期间创建反向映射时是一个问题。

编译错误:找不到时缺少
return
。Java 8流等效:
return map.entrySet().Stream().filter(e->e.getValue().contains(bar)).findFirst().map(Entry::getKey).orElse(null)
@Ioannis是否有一个数据结构可以在不经过这么多迭代的情况下完成它,或者它是否比这个更好?@KillerBeast这是最简单的解决方案,因为您必须搜索映射。您无法避免迭代。你说的更好是什么意思?你是说更快?当您拥有大数据(地图中有数百万条条目)时,还有其他选择。例如,Hadoop和Spark通过使用MapReduce做得更好,并通过将工作划分为一组在多个节点/线程中运行的独立任务来并行处理大量数据。MapReduce不是一个数据结构,而是一个编程模型。编译错误:找不到时缺少
return
。Java 8流等价物:
return map.entrySet().Stream().filter(e->e.getValue().contains(bar)).findFirst().map(Entry::getKey).orElse(null)
@Ioannis是否有一种数据结构可以在不经过这么多迭代的情况下完成这项工作,或者比这项工作做得更好?@KillerBeast这是最简单的解决方案,因为您必须搜索地图。您无法避免迭代。你说的更好是什么意思?你是说更快?当您拥有大数据(地图中有数百万条条目)时,还有其他选择。例如,Hadoop和Spark通过使用MapReduce做得更好,并通过将工作划分为一组在多个节点/线程中运行的独立任务来并行处理大量数据。MapReduce不是一种数据结构,而是一种编程模型。