Подтвердить что ты не робот

Почему Collections.shuffle() терпит неудачу для моего массива?

Почему мой код не работает?

package generatingInitialPopulation;

import java.util.Arrays;
import java.util.Collections;

public class TestShuffle {
    public static void main(String[] args) {
        int[] arr = new int[10];

        for (int i = 0; i < arr.length; i++) {
            arr[i] = i;
        }

        Collections.shuffle(Arrays.asList(arr));

        for (int i = 0; i < arr.length; i++) {
            System.out.print(arr[i] + " ");
        }
    }
}

Результат: 0 1 2 3 4 5 6 7 8 9.

Я ожидал случайную последовательность.

4b9b3361

Ответ 1

Arrays.asList() не может применяться к массивам примитивного типа, как вы ожидаете. Когда применяется к int[], Arrays.asList() создает список int[] вместо списка Integer s. Поэтому вы перемещаете вновь созданный список int[].

Это тонкое поведение вариативных аргументов и дженериков в Java. Arrays.asList() объявляется как

public static <T> List<T> asList(T... a)

Таким образом, он может принимать несколько аргументов некоторого типа T и создавать список, содержащий эти аргументы, или он может принимать один аргумент типа T[] и возвращать список, поддерживаемый этим массивом (как работают вариативные аргументы),

Однако последний параметр работает только тогда, когда T является ссылочным типом (т.е. не примитивным типом, таким как int), потому что только ссылочные типы могут использоваться как параметры типа в generics (и T - это тип).

Итак, если вы пройдете int[], вы получите T= int[], и код не работает должным образом. Но если вы передадите массив ссылочного типа (например, Integer[]), вы получите T= Integer и все будет работать:

Integer[] arr = new Integer[10]; 

for (int i = 0; i < arr.length; i++) { 
    arr[i] = i; 
} 

Collections.shuffle(Arrays.asList(arr)); 

for (int i = 0; i < arr.length; i++) { 
    System.out.print(arr[i] + " "); 
} 

Ответ 2

Попробуйте добавить эту строку кода в свой тест:

List l=Arrays.asList(arr);
System.out.println(l);

Вы увидите, что вы печатаете один элемент List.

Использование Arrays.asList в примитивном массиве вызывает asList для обработки int[] как одного объекта, а не массива. Он возвращает List<int[]> вместо List<Integer>. Таким образом, вы в основном перетаскиваете один элемент List, и поэтому ничего не перетасовывается.

Обратите внимание, что некоторые из уже заданных ответов неверны, потому что asList возвращает список, поддерживаемый исходным массивом, ничего не копируется - все изменения отражаются в исходном массиве.

Ответ 3

Это не работает, потому что вызов shuffle работает на List, возвращаемом Arrays.asList, а не на базовый массив. Таким образом, когда вы перебираете массив для печати значений, ничего не изменилось. Вы хотите сохранить ссылку на List, возвращаемую Arrays.asList, а затем распечатать значения этого List (а не значения массива) после того, как вы shuffle его.

Ответ 4

Сохраните список, сохраненный в Arrays.asList, и перетасуйте его...

List myShuffledList = Arrays.asList(arr);
Collections.shuffle(myShuffledList);