Java 返回与年份和等级关联的字符串
基本上我有一张这样的地图Java 返回与年份和等级关联的字符串,java,hashmap,set,maps,Java,Hashmap,Set,Maps,基本上我有一张这样的地图 HashMap<Integer, HashMap<String, Integer>> girls = new HashMap<Integer, HashMap<**String**, Integer>>();' 我不知道如何做上面的标题试试看 return girls.getOrDefault(year, Collections.emptyMap()).entrySet().stream() .
HashMap<Integer, HashMap<String, Integer>> girls =
new HashMap<Integer, HashMap<**String**, Integer>>();'
我不知道如何做上面的标题试试看
return girls.getOrDefault(year, Collections.emptyMap()).entrySet().stream()
.filter(e -> e.getValue() == rank)
.map(e -> e.getKey())
.findFirst()
.orElse(null);
如果可以避免,请不要使用地图地图。有些原因和情况下,你可能想,但这是非常混乱,因为你已经看到自己 这不是你想要的情况之一。只需声明一个新类来封装此信息并将其存储在列表中:
class Girl
{
// Declare getters if you want
public final int year;
public final int rank;
public final String name;
Girl(int year, int rank, String name){
this.year = year;
this.rank = rank;
this.name = name;
}
}
现在,您的数据结构并不是一团糟:
List<Girl> girls = new ArrayList<>();
您可以通过以下方式对地图进行流式处理:
//get the map that match the year:
Map<String, Integer> mapForKeyYear = g.getOrDefault(year, null);
//if the map is not null then filter that map to the rank:
String r = mapForKeyYear
.entrySet().stream()
.filter(e -> e.getValue() == rank)
.map(Map.Entry::getKey)
.findFirst().orElse(null);
//获取与年份匹配的地图:
Map mapForKeyYear=g.getOrDefault(年份,空);
//如果映射不为空,则将该映射过滤到秩:
字符串r=mapForKeyYear
.entrySet().stream()
.filter(e->e.getValue()==rank)
.map(map.Entry::getKey)
.findFirst().orElse(null);
如上所述,您的代码不会编译,原因超过您提到的原因
我认为你误解了如何使用地图。地图就像书中的词汇表一样使用。词汇表包含主题的页码。在类似意义上,映射包含给定(k[页码])的值(v[值])
但是你可以告诉电脑你想储存什么。因此,您需要了解键和值,以便正确构建映射。让我们尝试直观地查看
HashMap
的结构,因为它是一个相当复杂的数据结构
// A B
// |--------|--------|
// C D
// |------|---------------------------------------------------------------------|
{
Integer: {String: Integer, String: Integer, String: Integer, String: Integer},
Integer: {String: Integer, String: Integer, String: Integer, String: Integer},
Integer: {String: Integer, String: Integer, String: Integer, String: Integer},
Integer: {String: Integer, String: Integer, String: Integer, String: Integer}
}
部分A和C是键,B和D是值
现在让我们看看.get(year).get(rank)是什么代码>。首先,调用get(year)
year
是C节中的一个值,因此get(year)
在D节中返回一个值。接下来,调用get(rank)
。由于它是在get(year)
的返回值上调用的,rank
在a部分中有一个值。get(rank)
将在D部分中返回一个值,这些值都是整数。因此,会发生编译器错误
要解决这个问题,只需在内部映射中交换这两种类型。您从HashMap
更改为HashMap
感觉您的内部映射应该从Integer->String,而不是String->Integer:HashMap
。您正以相反的方式使用HashMap。您可以使用键来获取值,而不是使用值来获取键。将内部hashmap翻转为将整数映射为字符串将解决此问题。对于理解映射有困难的人来说,可能出现的重复将不会从包含lambdas和streams的解决方案中受益。播放给你的听众听。@Michael我在回答中没有看到集合的使用。emptyMap()无论如何感谢feedbak…你是对的,但是集合。emptyMap()
是一个改进,因为你的可能会出现空指针异常。所以我错了,几乎一样,但更糟;)词汇表提供了单词的定义(这也是地图的类比…)。你在想一个索引。在你的类比中,你还混淆了键和值。人们会去索引中寻找一个单词(键),然后得到一个页码(值)。你的类比也不成立,因为可以有多个页面(值)与一个单词(键)关联。这在标准的一对一映射中是不可能的。根本问题是,正如您所说,它是“一个复杂的数据结构”。解决方案应该是降低数据结构的复杂性。@Michael,是的。你的回答中已经提到了这一点,所以我只是提供一个替代方案。这很好,但说得更清楚也无妨如果映射的不同名称
(字符串
键)可以具有相同的秩
(整数
值)…@Spock(如果确实存在相同的秩),则无法应用您的解决方案。OP希望从get(rank)
中获得什么?OP显然是想从一个等级中得到这个名字。
//get the map that match the year:
Map<String, Integer> mapForKeyYear = g.getOrDefault(year, null);
//if the map is not null then filter that map to the rank:
String r = mapForKeyYear
.entrySet().stream()
.filter(e -> e.getValue() == rank)
.map(Map.Entry::getKey)
.findFirst().orElse(null);
// A B
// |--------|--------|
// C D
// |------|---------------------------------------------------------------------|
{
Integer: {String: Integer, String: Integer, String: Integer, String: Integer},
Integer: {String: Integer, String: Integer, String: Integer, String: Integer},
Integer: {String: Integer, String: Integer, String: Integer, String: Integer},
Integer: {String: Integer, String: Integer, String: Integer, String: Integer}
}