Computer >> 컴퓨터 >  >> 프로그래밍 >> JavaScript

JavaScript 배열에서 중복 없이 무작위 요소 n개 선택하는 방법

JavaScript에서 배열의 요소 중 일부를 중복 없이 무작위로 추출해야 하는 경우가 자주 있습니다. 예를 들어, 다음과 같이 중복 요소가 없는 배열 리터럴이 있다고 가정해 보겠습니다.

const arr = [2, 5, 4, 45, 32, 46, 78, 87, 98, 56, 23, 12];

문제 정의

우리가 작성해야 할 함수는 두 가지 인수를 받습니다.

  • 고유한(unique) 값들로만 이루어진 배열
  • 추출할 요소의 개수 n

함수는 입력 배열에서 무작위로 선택한 n개의 요소로 구성된 새로운 배열을 반환해야 하며, 어떤 요소도 결과 배열에 두 번 이상 등장해서는 안 됩니다.

구현 방법

핵심 아이디어는 간단합니다. 원하는 개수만큼 반복하면서 매번 Math.random()Math.floor()를 사용해 배열 내 임의의 인덱스를 생성하고, 이미 선택된 요소인지 검사한 후 중복되지 않은 경우에만 결과 배열에 추가합니다.

const arr = [2, 5, 4, 45, 32, 46, 78, 87, 98, 56, 23, 12];
const chooseRandom = (arr, num = 1) => {
    const res = [];
    for(let i = 0; i < num; ){
        const random = Math.floor(Math.random() * arr.length);
        if(res.indexOf(arr[random]) !== -1){
            continue;
        };
        res.push(arr[random]);
        i++;
    };
    return res;
};
console.log(chooseRandom(arr, 4));

코드 설명

  • 기본값 처리: 두 번째 인수 num이 전달되지 않으면 기본값 1이 사용되므로, 개수를 지정하지 않아도 요소 하나를 안전하게 추출할 수 있습니다.
  • 무작위 인덱스 생성: Math.floor(Math.random() * arr.length)는 0부터 배열 길이 - 1 사이의 정수 인덱스를 만듭니다.
  • 중복 검사: res.indexOf(arr[random]) !== -1 조건으로 이미 선택된 요소인지 확인하고, 중복이라면 continue로 건너뛰어 카운터를 증가시키지 않습니다.

실행 결과

콘솔에서 위 코드를 실행하면 다음과 같은 형태의 출력을 얻을 수 있습니다. 실행할 때마다 선택되는 요소와 순서는 달라집니다.

[ 5, 2, 4, 78 ]

참고 사항

이 방식은 직관적이지만, 요청한 개수(n)가 배열 길이보다 크면 무한 루프에 빠질 수 있다는 점에 유의해야 합니다. 실무에서는 Fisher-Yates 셔플 알고리즘으로 배열을 섞은 뒤 앞에서 n개를 잘라내는 방식이 더 효율적이고 안전합니다.