我正在学习Java 8流。告诉我,如何更紧凑地编写sortArray方法?

import org.junit.Test;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.HashMap;
import java.util.Map;

import static org.junit.Assert.assertArrayEquals;

public class TestStream {

    /*
     * Sort numbers in an array without changing even numbers position
     */

    @Test
    public void test_1() {
        int[] nonSorted = new int[]{3, 4, 5, 2, 1, 6, 9, 8, 7, 0};
        int[] expected = new int[]{1, 4, 3, 2, 5, 6, 7, 8, 9, 0};

        Integer[] arr = sortArray(nonSorted);
        int[] sorted = new int[arr.length];
        for (int i = 0; i < arr.length; i++) {
            sorted[i] = arr[i];
        }

        assertArrayEquals(expected, sorted);
    }

    private Integer[] sortArray(int[] array) {
        Map<Integer, Integer> even = extractEven(array);
        Integer[] withoutEvens = removeEven(array);
        int length = even.size() + withoutEvens.length;
        Integer[] result = new Integer[length];
        Arrays.sort(withoutEvens);
        for (int i = 0; i < withoutEvens.length; i++) {
            result[i] = withoutEvens[i];
        }
        even.forEach((k, v) -> {
            System.arraycopy(result, k, result, k + 1, length - k - 1);
            result[k] = v;
        });

        return result;
    }


    private Map<Integer, Integer> extractEven(int[] array) {
        Map<Integer, Integer> map = new HashMap<>();
        for (int i = 0; i < array.length; i++) {
            if (array[i] % 2 == 0) {
                map.put(i, array[i]);
            }
        }

        return map;
    }

    private Integer[] removeEven(int[] array) {
        ArrayList<Integer> list = new ArrayList<Integer>();

        for (int i = 0; i < array.length; i++) {
            if (array[i] % 2 != 0) {
                list.add(array[i]);
            }
        }

        Integer[] a = new Integer[list.size()];
        return list.toArray(a);
    }
}

最佳答案

可以想到一个解决方案,例如:
首先,我们从nonSorted[]中提取奇数整数,然后以排序的方式将它们放在stack上。



现在我们获取一个Instream,并将其从0运行到nonSorted.length-1,并检查原始nonSorted中是否存在奇数Integer;一旦找到一个,我们就将其替换为堆栈的第一个元素,并从pop()中对该元素进行stack


int[] nonSorted = new int[]{3, 4, 5, 2, 1, 6, 9, 8, 7, 0};

LinkedList<Integer> stack = Arrays.stream(nonSorted)
            .sorted().filter(s -> s % 2 != 0).boxed()
            .collect(Collectors.toCollection(LinkedList::new));

int[] expected = IntStream.rangeClosed(0, nonSorted.length - 1)
       .map(s -> nonSorted[s] % 2 != 0 ? stack.pop():nonSorted[s])
       .toArray();

09-27 20:23