我没有在下面发布这个相当简短的方法,为什么调用merger()
函数(以确定与同一个键相关的值会发生什么)。
该方法应该按应用程序对搜索配置列表进行分组,并按地图键(应用程序名称)以及地图值(按名称搜索配置)对其进行排序。也许第二个流不是直接的,我可以/应该使用另一种方法,但是我想知道发生了什么。
输出就是这样的:
ApplicationInfo实现不会覆盖int hashCode()
也不会覆盖boolean equals(Object)
。
我原以为每个搜索配置列表的第二个流中的映射键总是不同的。但是,在一个特定的情况下,调用merge-function,我不知道它为什么被调用。
public SortedMap<ApplicationInfo, List<SearchConfigInfo>> groupByApplications(final BusinessLogicProcessingContext ctx,
final List<SearchConfigInfo> searchConfigInfos) {
requireNonNull(ctx, "The processing context must not be null.");
requireNonNull(searchConfigInfos, "The search configuration informations must not be null.");
final String lang;
final RtInfoWithTitleComparator comp;
lang = ContextLanguage.get(ctx);
appComp = new RtInfoWithTitleComparator(lang);
final Map<ApplicationInfo, List<SearchConfigInfo>> appToSearchConfigs;
appToSearchConfigs = searchConfigInfos.stream()
.collect(groupingBy(searchConfig -> RtCache.getApplication(searchConfig.getApplicationGuid())));
return appToSearchConfigs.entrySet()
.stream()
.collect(toMap(Map.Entry::getKey,
p_entry -> _sortValueList(p_entry.getValue()),
merger(),
() -> new TreeMap<>(appComp)));
}
地图的一般合同是:
“将键映射到值的对象。映射不能包含重复键;每个键最多可映射一个值。”
这就是为什么我真的很想知道在这种情况下会发生什么。
private static BinaryOperator<List<SearchConfigInfo>> merger() {
return (list1, list2) -> { System.out.println(RtCache.getApplication(list1.get(0).getApplicationGuid()).hashCode());
System.out.println(RtCache.getApplication(list2.get(0).getApplicationGuid()).hashCode());
System.out.println(list1.get(0).getApplicationGuid().equals(list2.get(0).getApplicationGuid()));
list1.addAll(list2);
return list1;
};
}
正如我在简单的STDOUT调试语句中看到的那样,hashCodes是不同的,并且它们彼此不相等。
答案 0 :(得分:1)
请注意,作为TreeMap
方法提供的供应商函数的结果,您提供了Collectors.toMap()
(
toMap(Map.Entry::getKey,
p_entry -> _sortValueList(p_entry.getValue()),
merger(),
() -> new TreeMap<>(appComp)));
(供应商函数提供收集器将用于包含结果的集合 - 因此在这种情况下,它始终提供TreeMap
。)
A TreeMap
performs key comparisons with compareTo()
,这就是为什么在这种情况下可以获得密钥冲突的原因 - 相对于供应商地图而不是它们所源自的地图进行冲突。