[study] 언제까지 넘겨 짚을래 ch27. 배열

가오리·2023년 5월 8일
0

javascript

목록 보기
24/44
post-thumbnail
📌 스터디 교재 및 강의
  1. [youtube] 모던 자바스크립트 Deep Dive 스터디
  2. [e-book] 모던 자바스크립트 Deep Dive
  3. [e-book] 코어 자바스크립트
  4. [blog] 자바스크립트 개발자라면 알아야 할 33가지 개념

✏️ 배열(array)이란

여러 개의 값을 순차적으로 나열한 자료구조며, 배열이 가지고 있는 값을 요소(element)라고 부른다. 원시값은 물론 객체, 함수, 배열 등 모든 값은 배열의 요소가 될 수 있다.

  • 자신의 위치를 나타내는 0 이상의 정수인 인덱스(index)를 갖는다.
  • 배열은 요소의 개수(배열의 길이)를 나타내는 length 프로퍼티를 갖고 이 때문에 for문을 통해 순차적으로 요소에 접근이 가능하다.
  • 자바스크립트에 배열이라는 타입이 존재하지 않고 객체로 존재한다.
구분객체배열
구조프로퍼티 키와 프로퍼티 값인덱스와 요소
값의 참조프로퍼티 키인덱스
값의 순서XO
length 프로퍼티XO

✏️ 자바스크립트 배열은 배열이 아니다.

자바스크립트 배열은 해시 테이블로 구현된 객체이므로 일반적인 배열보다 성능적으로 느릴 수 밖에 없는 구조적 단점이 있지만 특정 요소를 검색하거나 요소를 삽입, 삭제하는 경우 일반적인 뱅려보다 빠른 성능을 기대할 수 있다.

🪝 자료구조에서의 배열: 동일한 크기의 메모리 공간이 빈틈없이 연속적으로 나연된 자료구조

🪝 밀집 배열(dense array): 배열의 요소가 하나의 데이터 타입으로 통일되어 있으며 서로 연속적으로 인접한 배열

🪝 희소 배열(sparse array): 메모리 공간이 동일한 크기가 아니어도 되며, 연속적이지 않을수도 있다.

✏️ length 프로퍼티와 희소 배열

length 프로퍼티의 값은 0 ~ (2^32 -1) 범위의 양의 정수다. length 프로퍼티의 값은 배열에 요소를 추가, 삭제하면 자동 갱신된다. 현재 length 프로퍼티 값보다 큰 숫자 값을 할당할 경우 값은 변경되지만 실제로 배열의 길이가 늘어나지는 않는다.(empty로 표현)

✏️ 배열 생성

  1. 배열 리터럴

    0개 이상의 요소를 쉼표로 구분하여 대괄호로 묶으며 요소를 하나도 추가하지 않으면 배열의 길이가 0인 빈 배열이 된다. 배열 리터럴에 요소를 생략하면 희소 배열이 생성된다.

    const arr1 = [1, 2, 3];
    const arr2 = [];
    const arr3 = [1, , 3];
    console.log(arr1.length); // 3
    console.log(arr2.length); // 0
    console.log(arr3.length); // 3
  2. Array 생성자 함수

    Array 생성자 함수를 통해 배열을 생성할 수 있는데 이는 전달된 인수의 개수에 따라 다르게 동작하기 때문에 주의가 필요하다. 전달된 인수가 없는 경우 빈 배열([])을 생성한다.

    new 연산자와 함께 호출하지 않더라도(= 일반 함수로서 호출해도) 생성자 함수로 동작하며 이는 생성자 함수 내에서 new.target을 확인하기 때문이다.

    const arr = new Array(10);
    console.log(arr); // [ <10 empty items> ]
    console.log(arr.length); // 10
  3. Array.of

    전달된 인수를 요소로 갖는 배열을 생성하는데 생성자 함수와 다르게 전달된 인수가 1개이고 숫자더라도 인수를 요소로 갖는 배열을 생성한다.

    const arr = Array.of(1, 2, 3);
    console.log(arr); // [1,2,3]
  4. Array.from

    유사 배열 객체나 이터러블 객체를 인수로 전달받아 배열로 변환하여 반환한다.

    let arr = Array.from({ length: 3, 0: 'gaori', 1: 'coco', 2: 'AkO' });
    // [ 'gaori', 'coco', 'AkO' ]
    arr = Array.from('gaori');
    // [ 'g', 'a', 'o', 'r', 'i' ]

✏️ 배열 요소의 참조

요소를 참조할 때는 대괄호를 사용하고 안에는 인덱스가 와야하며 값을 참조할 수 있다는 의미에서 객체의 프로퍼티 키와 같은 역할을 한다. 존재하지 않는 요소에 접근하면 undefined를 반환한다.(→ 배열은 인덱스를 나타내는 문자열을 프로퍼티 키로 갖는 객체이기 때문)

✏️ 배열 요소의 추가와 갱신

객체에 프로퍼티를 동적으로 추가할 수 있는 것처럼 배열에도 요소를 동적으로 추가할 수 있다. 존재하지 않는 인덱스를 써서 할당하면 새로운 요소가 추가된다.

인덱스는 요소의 위치를 나타내므로 반드시 0 이상의 정수를 사용해야 하며 정수 이외의 값을 인ㄷ게스처럼 사용하면 요소가 생성된느 것이 아닌 프로퍼티가 생성된다. 이때 추가된 프로퍼티는 length의 값에 영향을 주지 않는다.

const arr = ['gaori'];
arr[1] = 'coco';
console.log(arr); // [ 'gaori', 'coco' ]
console.log(arr.length); // 2

arr['bird'] = 'hamon';
console.log(arr); // [ 'gaori', 'coco', bird: 'hamon' ]
console.log(arr.length); // 2

✏️ 배열 요소의 삭제

배열은 객체이기 때문에 배열의 특정 요소를 삭제하기 위해 delete 연산자를 사용할 수 있다. 이때 배열은 희소 배열이 되며 length 프로퍼티의 값은 변하지 않는다.

const arr = [1, 2, 3];
delete arr[1];
console.log(arr); // [ 1, <1 empty item>, 3 ]
console.log(arr.length); // 3

희소 배열을 만드는 delete 연산자는 사용하지 않는 것이 좋으며 그렇기 위해 Array.prototype.splice 메서드를 사용하는 것이 좋다.

const arr = [1, 2, 3];
arr.splice(1, 1);
console.log(arr); // [1, 3]
console.log(arr.length); // 2

✏️ 배열 메서드

배열에는 원본 배열을 직접 변경하는 메서드와 원본 배열을 직접 변경하지 않고 새로운 배열을 생성하여 반환하는 메서드가 있는데 가급적 원본 배열을 직접 변경하지 않는 메서드를 사용하는 편이 좋다.

  1. Array.isArray

    전달된 인수가 배열이면 true, 아니면 false를 반환한다.

  2. Array.prototype.indexOf

    원본 배열에 인수로 전달한 요소와 중복되는 요소가 여러 개 있다면 첫 번재로 검색된 요소의 인덱스를 반환하고 존재하지 않으면 -1을 반환한다.

    const arr = [1, 2, 2, 3];
    arr.indexOf(2); // 1
    arr.indexOf(4); // -1
  3. Array.prototype.push

    인수로 전달받은 모든 값을 원본 배열의 마지막 요소로 추가하고 변경된 length 프로퍼티 값을 반환하는데 이는 원본 배열을 직접 변경한다.

  4. Array.prototype.pop

    원본 배열에서 마지막 요소를 제거하고 제거한 요소를 반환한다. 원본 배열이 빈 배열이면 undefined를 반환하며 원본 배열을 직접 변경한다.

  5. Array.prototype.unshift

    인수로 전달받은 모든 값을 원본 배열의 선두에 요소로 추가하고 변경된 length 프로퍼티 값을 반환하는데 이는 원본 배열을 직접 변경한다.

  6. Array.prototype.shift

    원본 배열에서 첫 번째 요소를 제거하고 제거한 요소를 반환한다. 원본 배열이 빈 배열이면 undefined를 반환하며 원본 배열을 직접 변경한다.

  7. Array.prototype.concat

    인수로 전달된 값(배열이나 원시값)을 원본 배열의 마지막 요소로 추가한 새로운 배열을 반환한다. 인수로 전달한 값이 배열인 경우 배열을 해체하여 새로운 배열의 원소로 추가하고 원본 배열은 변경되지 않는다.

  8. Array.prototype.splice

    원본 배열의 중간에 요소를 추가하거나 중간에 있는 요소를 제거하는 경우 splice을 사용하는데 이는 원본 배열을 직접 변경한다.

    arr.splice(start, deleteCount, items);

    start: 원본 배열의 요소를 제거하기 시작할 인덱스, start부터 모든 요소를, -1일 경우 마지막 요소 제거

    deleteCount: start부터 제거할 요소의 개수, 0이면 요소 제거X

    items: 제거한 위치에 삽입할 요소들의 목록, 생략 시 원본 배열 요소들을 제거하기만

  9. Array.prototype.slice

    인수로 전달된 범위의 요소들을 복사하여 배열로 반환하며 원본 배열은 변경되지 않는다.

    arr.slice(start, end);

    start: 복사 시작할 인덱스, 음수인 경우 배열의 끝에서 인덱스를 나타낸다.

    end: 복사를 종료할 인덱스, 생략 시 기본값인 length 프로퍼티 값

  10. Array.prototype.join

    원본 배열의 모든 요소를 문자열로 변환한 후 인수로 전달받은 문자열, 구문자로 연결한 문자열을 반환하며 구문자 생략 시 기본 구문자 콤마를 사용한다.

  11. Array.prototype.reverse

    원본 배열의 순서를 뒤집는다. 원본 배열이 변경되며 변경된 배열을 반환한다.

  12. Array.prototype.fill

    인수로 전달받은 값을 배열의 처음부터 끝까지 요소로 채우는데 이때 원본 배열이 변경된다.

  13. Array.prototype.includes

    배열 내에 특정 요소가 포함되어 있는지 확인하여 true, false를 반환한다.

    첫 번째 인수로 검색할 대상을 지정하고 두 번째 인수로 검색을 시작할 인덱스를 전달한다.(생략 시 기본값 0)

  14. Array.prototype.flat

    인수로 전달한 깊이만큼 재귀적으로 배열을 평탄화한다. 중첩 배열을 평탄화할 깊이를 인수로 전달할 수 있으며 인수를 생략할 경우 기본값은 1이다.(Infinity를 전달하면 중첩 배열 모두 편탄화)

    [1, [2, [3, [4]]]].flat(); // [1, [2, [3, [4]]]]
    [1, [2, [3, [4]]]].flat(Infinity); // [1, 2, 3, 4]

✏️ 배열 고차 함수

고차함수는 함수를 인수로 전달받거나 함수를 반환하는 함수를 말하는데 자바스크립트의 함수는 일급 객체이므로 함수를 갑처럼 인수로 전달할 수 있으며 반환할수도 있다. 고차함수는 외부 상태의 변경이나 가변 데이터를 피하고 불변성을 지향하는 함수형 프로그래밍에 기반을 두고 있다.

🪝 함수형 프로그래밍: 순수함수를 통해 부수효과를 최대한 억제하는 프로그래밍 패러다임

  1. Array.prototype.sort

    배열의 요소를 정렬하는데 원본 배열을 직접 변경하며 정렬된 배열을 반환한다. 기본적으로 오름차순으로 요소 정렬

  2. Array.prototype.forEach

    forEachfor문을 대체할 수 있다. 내부에서 반복문을 실행하며 이를 통해 자신을 호출한 배열을 순회하며 수행해야할 처리를 콜백함수로 전달받아 반복호출한다. forEach 메서드는 원본 배열을 변경하지 않지만 콜백함수를 통해 원본 배열을 변경할 수 있다.

  3. Array.prototype.map

    자신을 호출한 배열의 모든 요소를 순회하면서 인수로 전달받은 콜백 함수를 반복 호출하고 콜백 함수의 반환값들로 구성된 새로운 배열을 반환하는데 이 때 원본 배열은 변경되지 않는다.

  4. Array.prototype.filter

    자신을 호출한 배열의 모든 요소를 순회하면서 인수로 전달받은 콜백 함수를 반복 호출하고 콜백 함수의 반환값이 true인 요소로만 구성된 새로운 배열을 반환하는데 이때 원본 배열은 변경되지 않는다.

  5. Array.prototype.reduce

    인수로 전달받은 콜백 함수를 반복 호출하고 콜백함수의 반환값을 다음 순회 시에 콜백 함수의 첫 번째 인수로 전달하면서 콜백함수를 호출하여 하나의 결과값을 만들어 반환한다.

  6. Array.prototype.some

    배열의 요소 중에 콜백 함수를 통해 정의한 조건을 만족하는 요소가 1개 이상 존재하는지 확인하여 그 결과를 불리언 타입으로 반환한다. some 메서드를 호출한 배열이 빈 배열일 경우 언제나 false를 반환한다.

  7. Array.prototype.every

    배열의 모든 요소가 콜백 함수를 통해 정의한 조건을 모두 만족하는지 확인하여 그 결과를 불리언 타입으로 반환한다. every 메서드를 호출한 배열이 빈 배열인 경우 언제나 true를 반환한다.

  8. Array.prototype.find

    자신을 호출한 배열의 요소를 순회하면서 인수로 전달된 콜백 함수를 호출하여 반환값이 true인 첫 번째 요소를 반환한다. 콜백 함수의 반환값이 true인 요소가 존재하지 않는다면 undefined를 반환한다.

  9. Array.prototype.findIndex

    자신을 호출한 배열의 요소를 순회하면서 인수로 전달된 콜백 함수를 호출하여 반환값이 true인 첫 번재 요소의 인덱스를 반환하고 콜백 함수의 반환값이 true인 요소가 존재하지 않는다면 -1을 반환한다.

  10. Array.prototype.flatMap

    map 메서드와 float 메서드를 순차적으로 실행하는 효과가 있는데 flat 메서드처럼 인수를 전달하여 평탄화 깊이를 지정할 수 없고 1단계만 평탄화한다.

profile
가오리의 코딩일기

0개의 댓글