亚洲在线久爱草,狠狠天天香蕉网,天天搞日日干久草,伊人亚洲日本欧美

為了賬號安全,請及時綁定郵箱和手機立即綁定
已解決430363個問題,去搜搜看,總會有你想問的

使用流交替混合兩個列表

使用流交替混合兩個列表

藍山帝景 2023-03-23 16:35:50
我使用循環實現了這個,但我不知道如何使用流來實現。我們得到兩個列表,例如 1 2 3 和 4 5 6,混合后結果將是 1 4 2 5 3 6。public <T> List<T> mixingList(List<T> list1, List<T> list2) {    List<T> result = new ArrayList<>();    int maxSize = list1.size() > list2.size() ? list1.size() : list2.size();    for (int i = 0; i < maxSize; i++) {        if (i < list1.size()) {            result.add(list1.get(i));        }        if (i < list2.size()) {            result.add(list2.get(i));        }    }    return result;}我為此準備測試。首先有 3 個測試 - 第二個列表大小相同 - 第三個是一個空列表 - 大小不同@Testpublic void shouldReturnShakedList() {    //given    List<Integer> list1 = new ArrayList<>(Arrays.asList(1, 3, 5));    List<Integer> list2 = new ArrayList<>(Arrays.asList(2, 4, 6));    //when    List<Integer> results = new ShakeListUtil().mixingList(list1, list2);    //then    Assertions.assertThat(results).containsExactly(1, 2, 3, 4, 5, 6);    Assertions.assertThat(results).hasSize(6);}@Testpublic void shouldReturnJustList2IfList1IsEmpty() {    //given    List<Integer> list1 = new ArrayList<>();    List<Integer> list2 = new ArrayList<>(Arrays.asList(2, 4, 6));    //when    List<Integer> results = new ShakeListUtil().mixingList(list1, list2);    //then    Assertions.assertThat(results).containsExactly(2, 4, 6);    Assertions.assertThat(results).hasSize(3);}@Testpublic void shouldReturnShakedListIfTheSizeListIsDifferent() {    //given    List<Integer> list1 = new ArrayList<>(Arrays.asList(1, 3));    List<Integer> list2 = new ArrayList<>(Arrays.asList(2, 4, 6));    //when    List<Integer> results = new ShakeListUtil().mixingList(list1, list2);    //then    Assertions.assertThat(results).containsExactly(1, 2, 3, 4, 6);    Assertions.assertThat(results).hasSize(5);}知道如何在 Java 流上做到這一點嗎?
查看完整描述

3 回答

?
米琪卡哇伊

TA貢獻1998條經驗 獲得超6個贊

這是使用流的解決方案:


public static <T> List<T> mixingList(List<T> list1, List<T> list2) {

    int shorter = Math.min(list1.size(), list2.size());

    int longer = Math.max(list1.size(), list2.size());

    Stream<T> firstPart = IntStream.range(0, shorter).mapToObj(x -> Stream.of(list1.get(x), list2.get(x))).flatMap(x -> x);

    if (longer > shorter) {

        Stream<T> secondPart = (list1.size() > list2.size() ? list1 : list2).subList(shorter, longer).stream();

        return Stream.concat(firstPart, secondPart).collect(Collectors.toList());

    } else {

        return firstPart.collect(Collectors.toList());

    }

}

魔法發生在mapToObj和中flatMap。它將每個索引映射到兩個列表元素的流,一個來自每個給定的列表。然后它用 . 壓扁流的流flatMap。


之后,如果兩個列表的大小不同,它會獲取較長列表的其余部分并將其連接到末尾。


查看完整回答
反對 回復 2023-03-23
?
胡子哥哥

TA貢獻1825條經驗 獲得超6個贊

一種方法可能是使用 anIntStream獲取列表索引流,Optional根據列表是否包含此索引將它們映射到 s,然后解析它們,但老實說,我不確定這是否更優雅比你原來的方法:


public <T> List<T> mixingList(List<T> list1, List<T> list2) {

    int maxSize = Math.max(list1.size(), list2.size());


    return IntStream.range(0, maxSize)

            .mapToObj(i -> Stream.of(listIndexToOptional(list1, i), 

                                     listIndexToOptional(list2, i)))

            .flatMap(Function.identity())

            .filter(Optional::isPresent)

            .map(Optional::get)

            .collect(Collectors.toList());

}


private static <T> Optional<T> listIndexToOptional(List<T> list, int index) {

    return index < list.size() ? Optional.of(list.get(index)) : Optional.empty();

}


查看完整回答
反對 回復 2023-03-23
?
暮色呼如

TA貢獻1853條經驗 獲得超9個贊

您可以將其分成兩部分。首先,你得到兩個列表的最小數量,然后混合兩個列表直到這個索引。之后,您將剩余的項目附加到更大的列表中。要結合兩者,您可以使用Stream.concat():


private static <T> List<T> mixingList(List<T> list1, List<T> list2) {

    int min = Math.min(list1.size(), list2.size());

    return Stream.concat(

            IntStream.range(0, min).boxed()

                    .flatMap(i -> Stream.of(list1.get(i), list2.get(i))),

            (list1.size() < list2.size() ? list2 : list1).stream().skip(min)

    ).collect(Collectors.toList());

}

或者,您可以Stream.concat()在使用時使用Stream.flatMap():


private static <T> List<T> mixingList(List<T> list1, List<T> list2) {

    return IntStream.range(0, Math.max(list1.size(), list2.size())).boxed()

            .flatMap(i -> Stream.concat(

                    i < list1.size() ? Stream.of(list1.get(i)) : Stream.empty(),

                    i < list2.size() ? Stream.of(list2.get(i)) : Stream.empty()))

            .collect(Collectors.toList());

}


查看完整回答
反對 回復 2023-03-23
  • 3 回答
  • 0 關注
  • 201 瀏覽
慕課專欄
更多

添加回答

舉報

0/150
提交
取消
微信客服

購課補貼
聯系客服咨詢優惠詳情

幫助反饋 APP下載

慕課網APP
您的移動學習伙伴

公眾號

掃描二維碼
關注慕課網微信公眾號