我使用预定义的myComparator在流中对一组填充的MyObject(该对象具有getName()getter)进行排序。
然后一旦排序,是否有办法将地图中的MyObject名称和对象的顺序/位置收集到地图中?
以下是我认为应该是这样的:
Set<MyObject> mySet; // Already populated mySet
Map<String, Integer> nameMap = mySet.stream()
.sorted(myComparator)
.collect(Collectors.toMap(MyObject::getName, //HowToGetThePositionOfTheObjectInTheStream));
例如,如果集合包含三个对象(object1的名称为name1,object2的名称为name2,object3的名称为name3),并且在流中它们被排序,我如何得到如下所示的结果映射:
name1, 1
name2, 2
name3, 3
感谢。
答案 0 :(得分:3)
Java Stream
不会公开元素的任何索引或位置,因此我无法用流魔法替换/*HowToGetThePositionOfTheObjectInTheStream*/
以获得所需的数字。
相反,一种简单的方法是收集到List
,它为每个元素提供索引。它是从零开始的,所以在转换为地图时,添加1。
List<String> inOrder = mySet.stream()
.sorted(myComparator)
.map(MyObject::getName)
.collect(Collectors.toList());
Map<String, Integer> nameMap = new HashMap<>();
for (int i = 0; i < inOrder.size(); i++) {
nameMap.put(inOrder.get(i), i + 1);
}
答案 1 :(得分:1)
最简单的解决方案是循环,作为一个正式正确的流解决方案,也可以并行工作,需要一个非常重要的(与其余的)合并函数:
Map<String,Integer> nameMap = mySet.stream()
.sorted(myComparator)
.collect(HashMap::new, (m, s) -> m.put(s.getName(), m.size()),
(m1, m2) -> {
int offset = m1.size();
m2.forEach((k, v) -> m1.put(k, v + offset));
});
与循环/收集操作比较:
List<MyObject> ordered = new ArrayList<>(mySet);
ordered.sort(myComparator);
Map<String, Integer> result = new HashMap<>();
for(MyObject o: ordered) result.put(o.getName(), result.size());
两种解决方案都采用独特的元素(因为只能有一个位置)。更改循环以检测违规很容易:
for(MyObject o: ordered)
if(result.putIfAbsent(o.getName(), result.size()) != null)
throw new IllegalStateException("duplicate " + o.getName());
答案 2 :(得分:0)
试试这个。您可以使用my_function <- function(data, column) {
quo_column <- enquo(column)
new_col <- paste0(quo_column, "_adjusted")[2]
mean_col <- paste0(quo_column, "_meanAdjusted")[2]
data %>%
mutate(!!new_col := (!!quo_column) + 1) %>%
group_by(Species) %>%
summarise(!!mean_col := mean(!! rlang::sym(new_col)))
}
head(my_function(iris, Petal.Length))
# A tibble: 3 x 2
# Species Petal.Length_meanAdjusted
# <fct> <dbl>
#1 setosa 2.46
#2 versicolor 5.26
#3 virginica 6.55
获取每个地图条目的值。并保证地图使用的顺序AtomicInteger
。
LinkedHashMap
答案 3 :(得分:0)
不要使用流:
{{1}}
这不仅比基于流的方法执行得更快,而且每个人都知道发生了什么。
Streams占有一席之地,但是Java 8之前的代码也是如此。