연속된 값을 갖는 배열을 얻는 방법

Park, Jinyong·2020년 4월 29일
6

Small, but Valuable.

목록 보기
15/19
post-custom-banner

Does JavaScript have a method like “range()” to generate a range within the supplied bounds?

가끔 [1, 2, 3, 4, 5, ...] 처럼 연속적인 값의 배열을 얻고 싶을 때가 있다. 혹은, 연속된 알파벳 배열이 필요할 수도 있다. 어떤 언어는 내장 함수나 혹은 구문으로 지원하지만, 자바스크립트에서는 아쉽게도 없다. 하지만, 이를 해결하기 위한 몇 가지 수법이 있다.(메서드를 이용한 방법은 아주 멋지다.)


range() 함수

가장 직관적인 방법은 반복문을 이용한 range() 함수를 작성하는 것이다.

시작(start)부터 끝(end)의 연속된 숫자로 구성된 배열을 반환한다. 끝의 수는 포함하지 않는다.

function range(start, end) {
  let array = [];
  for (let i = start; i < end; ++i) {
    array.push(i);
  }
  return array;
}
console.log(range(1, 10)); // [1, 2, 3, 4, 5, 6, 7, 8, 9]

시작만 지정하고 원하는 배열의 길이를 지정하도록 작성할 수도 있다.

function range(start, count) {
  let array = [];
  while(count--) {
    array.push(start++);
  }
  return array;
}

일정한 간격을 두고 반복하도록 작성할 수 있다.

function range(start, end, step=1) {
  let array = [];
  for (let i = start; i < end; ++i) {
    if (!(i % step)) {
      array.push(i);
    }
  }
  return array;
}
console.log(range(0, 5)); // [0, 1, 2, 3, 4]
console.log(range(0, 20, 5)); // [0, 5, 10, 15]

이 외에도 어떻게 작성하느냐에 따라 연속된 문자를 가진 문자열을 반환하는 함수를 작성할 수 있다.


String, Array 메서드 이용

메서드를 이용하면 반복문을 이용해 일일히 모두 작성하는 것보다 간단하게 작성할 수 있다.

Array().keys()

Array().keys()를 이용한 방법이다. Array(size)를 넣으면 크기가 size인 배열이 생성되는데 모든 값은 empty를 가진다. 이를 keys() 메서드를 사용하면 배열의 인덱스를 순회하는 iterator를 반환하고 이를 spread 연산자를 이용해 배열로 만들 수 있다.

[...Array(5).keys()]; // [0, 1, 2, 3, 4]

map 메서드를 사용하여 범위를 지정할 수 있다.

[...Array(5).keys()].map(key => key + 10); // [10, 11, 12, 13, 14]

물론 이를 함수화하여 범용성을 높힐 수 있다.

function range(size, start = 0) {
  return [...Array(size).keys()].map(key => key + start); 
}

console.log(range(5, 10)); // [10, 11, 12, 13, 14]

String.fromCharCode()

String.fromCharCode 메서드를 이용하여 연속된 문자를 가지는 문자열을 얻을 수도 있다.

// "ABCDEFGHIJKLMNOPQRSTUVWXYZ"
String.fromCharCode(...[...Array('Z'.charCodeAt(0) - 'A'.charCodeAt(0) + 1).keys()].map(key => key + 'A'.charCodeAt(0)));

range 함수와 같이 사용하여 함수화를 할 수 있다.

function characterRange(startChar, endChar) {
  const range = (size, start) => [...Array(size).keys()].map(key => key + start);
  return String.fromCharCode(...range(endChar.charCodeAt(0) - startChar.charCodeAt(0) + 1, startChar.charCodeAt(0)));
}
console.log(characterRange('E', 'T')); 'EFGHIJKLMNOPQRST'

Array.from()

Array.from() 메서드를 이용한 방법 또한 있다. 두 번째 인자는 map 메서드처럼 동작한다. 이 방법이 매우 깔끔하다..

function range(size, start = 0) {
  return Array.from({length: size}, (_, index) => index + start);
}
console.log(range(5, 10)); // [10, 11, 12, 13, 14]

Array().fill()

이 방법도 매우 깔끔하다.

function range(size, start) {
  return Array(size).fill(start).map((x, y) => x + y)
}
console.log(range(5, 10)); // [10, 11, 12, 13, 14]

어떻게 작성하느냐에 따라 매우 다양한 방법이 있다. 핵심은 숫자 나열은 Array.from()의 방법으로, 알파벳의 나열은 String.fromCharCode()의 방법으로 해결하면 간결하게 작성할 수 있다는 점이다. 물론 가장 쉬운 방법으로는 외부 라이브러리(e.g. lodash)를 사용하는 것이 될테지만...

post-custom-banner

1개의 댓글

comment-user-thumbnail
2022년 9월 27일

스프레드 문법과 keys 메소드 이용해서 초기화하는 방법 진짜 멋있네요!!

답글 달기