자바스크립트 배열 정복기

브리·2022년 7월 27일
0

를 외치면서 글을 작성하지만 정복까진.. 못할수도..^^ 세미 정복기.🏋🏻‍♀️

자바스크립트는 배열에 대한 유용한 메서드를 많이 제공한다.

자바스크립트 배열은 배열이 아니다?

자료구조에서 말하는 배열

동일한 크기의 메모리 공간이 연속적으로 나열된 자료구조이며 인덱스를 통해 한 번의 연산과(시간 복잡도 : O(1)) 빠른 속도로 요소에 접근할 수 있다.
다만, 정렬되지 않은 배열에서 특정 요소를 검색하기 위해서는 모든 요소에 접근하여야하는 시간복잡도 O(n)의 선형검색을 해야하고,
배열에 요소를 삽입, 삭제하는 경우 요소를 이동시켜 주어야한다. = 밀집 배열

자바스크립트에서의 배열


동일한 크기를 갖지 않아도, 연속적으로 이어져있지 않아도 된다. = 희소 배열
희소배열은 배열의 요소가 연속적이지 않고 일부가 비어있는 경우도 있다.
자바스크립트의 배열은 배열을 흉내내는 객체이다!

index 문자열을 를 프로퍼티 키로 가지고, 요소를 value으로 가지며 length 프로퍼티를 가지고 있는 특수한 객체이다. 그렇기 때문에 어떤 타입의 값이라도 배열의 요소가 될 수 있다.

0. 배열 생성방법

  1. 배열 리터럴
  2. Array 생성자 함수
  3. Array.of, Array.from 메서드

0.0. 배열 리터럴을 통한 배열 생성

const arr=["a","b","c"]; //배열 리터럴을 통한 배열 생성
const arr=[1,,3];//희소배열의 특징으로써 중간에 빈 값을 넣는다.
console.log(typeof arr); //object

0.1. Array 생성자 함수

const arr=new Array(10);
console.log(arr);//10개의 빈 값이 들어감
console.log(arr.length);//10

//이렇게 쓸 일은 거의 없겠지만 배열 요소의 최대값은 4,294,967,295개이다.
new Array(1000000000000); // rangeError
new Array(-1); // rangeError

//만약 인수가 숫자 하나가 아니라면 인수들을 요소로 갖는 배열을 생성한다.
new Array(1,2,3,4);//[1,2,3,4]

생성자 함수 Array는 new 키워드와 같이 쓰지 않아도 된다.

0.2. Array.of 와 Array.from

ES6에 도입된 새로운 메서드이다!
Array.of 는 전달된 인수를 요소로 갖는 배열을 생성한다.
일반 생성자 함수와는 다르게 전달된 인수가 1개고 숫자이더라도 인수를 요소로 갖는 배열을 생성한다.

const arr=new Array(4);[ ,  ,  ,  ]
const arrOf=new Array.of(4);[4]

Array.from 은 유사배열객체/이터러블 객체를 인수로 받아 배열로 반환한다.

Array.from({length:2, 0:'a', 1:'b'}); => ['a','b']
Array.from("Hello"); => ["H","e","l","l","o"]

//두번째 인수로 전달한 콜백함수를 통해 값을 만들면서 요소를 채울 수 있음.
Array.from({length:3}, (_,i)=>i); => [0,1,2]

1. 배열요소

  • 배열 요소의 참조
    배열 요소에 참조하려면 대괄호를 사용함.
    존재하지 않는 인덱스, 요소에 접근하면 undefined 가 반환.

  • 추가와 갱신
    동적 추가가 가능하며 이 때 length 는 자동 갱신된다.

const arr=[0];
arr[1]=1;
console.log(arr);//[0,1]
arr[100]=100;
console.log(arr);//[0,1,빈배열들~~~~, 100] => 희소배열

arr[1]=10;
console.log(arr);//[1,10, ~~ ,100]

//이 때 만약 인덱스에 0이상의 정수가 아닌 값이 들어가면 프로퍼티가 된다.
arr['foo']=3;
arr.bar=4;
arr[1.1]=5;
arr[-1]=6;
console.log(arr);//[1, 10, foo:3, bar:4, 1.1:5, -1:6]
console.log(arr.length);//2

프로퍼티는 length 값에 영향을 주지 않음!!

  • 배열 요소의 삭제
    배열은 객체이기 때문에 특정 요소를 삭제할 때 delete 연산자를 사용할 수 있다!
    그러나 delete 를 사용하면 프로퍼티를 삭제하는 것이고 그 배열은 희소배열이 되기 때문에 이왕이면 사용하지 않는 것이 좋다!!!!! ㅇㅋ 이해함

희소배열을 만들지 않으면서 삭제하려면 Array.prototype.splice 를 사용하면 된다.

splice(삭제 시작 인덱스, 삭제할 요소 수)

const arr=[1,2,3];
arr.splice(1,1); // 1인덱스부터 하나의 요소를 삭제한다는 의미
arr.splice(0,2); // 0인덱스부터 두개의 요소를 삭제한다는 의미

2. 배열 메서드

배열 메서드는 원본 배열을 직접 수정하는 메서드가 있고, 새로운 배열을 생성하는 메서드가 있다.
새로운 요소를 추가하는 메서드 중 push는 원래 배열에서 추가, concat 은 새로운 배열 생성(불변성 유지할 때 concat 을 쓰는 이유가 이거였구나 새삼 다시 깨닫네)

2.1. 배열의 길이 : length

const arr=["a","b","c"]; //배열 리터럴을 통한 배열 생성
console.log(arr.length);//3

배열은 인덱스와 length 를 가지고 있기 때문에 for 문을 통해 요소에 접근이 가능하다.
length 는 가장 큰 인덱스에서 1을 더한 값이고 빈 배열일 경우 0을 반환한다.

2.2. isArray : 생성자 함수의 정적메서드

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

Array.isArray([1,2,3]); 

2.3. indexOf(검색할 요소, 시작위치)

const arr=[1,2,2,3,5];
arr.indexOf(2); //2가 맨 먼저 나오는 인덱스를 반환함 : 1
arr.indexOf(4); //없으면 -1
arr.indexOf(2,2);//2를 검색하는데 2 인덱스부터 검색 시작해라->2

주로 배열에 특정 요소가 존재하는지 확인할 때 많이 쓰임.
그러나 이 경우에는 ES7에 도입된 includes 를 쓰면 더 좋ㄷㅏ.

  • includes
const arr=[1,2,3];
arr.includes(4);//false
arr.includes(1);//true

2.4. push and pop : 원본 배열 수정

  • push: 인수로 전달 받은 모든 값을 원본배열에 추가하고 length 값을 반환한다.
  • pop: 마지막 요소를 제거하고 제거한 요소를 반환한다. 빈 배열이면 undefined 반환

-> 스택 구현에 용이

2.5. unshift and shift : 원본 배열 수정

  • unshift : 인수로 전달 된 값을 선두에 추가한다.
  • shift : 앞에 있는 걸 제거하고 제거한 요소를 반환한다.

-> 큐 구현에 용이

2.6. concat : 새로운 배열의 요소 반환

const arr1=[1,2];
const arr2=[3,4];

const result=arr1.concat(arr2);
console.log(result);//[1,2,3,4]

result=arr1.concat(3);
console.log(result);//[1,2,3]

result=arr1.concat(arr2, 5);
console.log(result);[1,2,3,4,5]

console.log(arr1);//[1,2]

2.7. splice(시작인덱스, 제거 요소 개수, 삽입요소) : 원본 배열 변경

삭제한 값을 반환한다.
제거 요소 개수를 0으로 지정하면 그냥 추가만 한다.
삽입요소가 없으면 그냥 삭제만 함.

const arr1=[1,2,3,4];

const result=arr.splice(1,2,20,30);
//1 인덱스부터 2개 삭제하고 20,30 넣어라
console.log(result);//[2,3]
console.log(arr1);//[1,20,30,4]

result=arr.splice(1);//제거 요소 개수도 없고 삽입요소도 없음. 시작인덱스만 있기 때문에 index 1부터 전부 삭제함.
console.log(arr);//[1]

2.8. slice(복사 시작인덱스, 복사 종료인덱스) : 새로운 배열 반환

const arr=[1,2,3];
arr.slice(0,1);//0부터 1 전 까지 [1]
arr.slice(0,3);//0부터 3 전까지 [0,1,2]
arr.slice(1,3);//1부터 3 전까지 [1,2]

2.9. join : 새로운 배열 반환

원본 배열의 모든 요소를 문자열로 변환하고 인수로 전달 받은 문자열을 구분자로 써서 반환함. 생략시 기본 구분자는 콤마임

const arr=[1,2,3,4];
arr.join();//'1,2,3,4'
arr.join('');//'1234'
arr.join(':');//`1:2:3:4`

2.10. reverse() : 원본 배열 변경

const arr=[1,2,3,4];
arr.reverse();//[4,3,2,1]

2.11. fill(채울 요소, 시작인덱스, 끝인덱스) : 원본 배열 변경

fill에 인자로 전달받은 요소로 시작~끝까지 채움. 시작인덱스, 끝인덱스는 선택임.

2.12. includes

배열 안에 있는지 없는지 보고 true, false 반환함.
두번째 인수로 검색 시작할 인덱스를 전달할 수 있음. 음수면 length에서 그 값을 더해서 그 부터 검색함.

arr.includes(2); //이런식으로 사용

2.13. flat 첨봄

ES10에서 도입된거라고 함. 처음 볼만함. 인수로 전달한 깊이만큼 재귀적으로 평탄화한다.
중첩 배열을 평탄화하는것 같은데 안쪽부터가 아니라 바깥쪽부터 평탄화함

와 진짜 많다.....
배열 고차함수는 시작도 안했는데...

3. 배열 고차함수

3.1. sort: 원본 배열 변경, 변경된 배열 반환

3.2. forEach

배열을 순회하면서 수행할 연산을 콜백으로 받는다.

const pows=[];
arr.forEach(item=>console.log(item));
arr.forEach(item=>pows.push(item**2));

3.3. map(item, index, arr) : 새로운 배열 반환

배열을 순회하면서 인수로 전달받은 콜백함수를 계속 반복 호출함.
map 메서드가 생성하여 반환하는 배열의 length 값은 기존의 배열과 1대1 대응하므로 같다.

arr.map(item, index, arr)=>{
	console.log(item);//요소값
  	console.log(index);//인덱스
  	console.log(arr);//호출한 객체(배열)
}

3.3. filter(item, index, arr) : 새로운 배열 반환

배열을 순회하면서 인수로 전달받은 콜백함수를 계속 반복 호출하며 콜백함수의 반환값이 true 인 배열을 반환한다.
filter 메서드가 생성하여 반환하는 배열의 length 값은 기존의 배열과 같거나 작음.

arr.filter(item=>item.id!==id);

3.4. reduce(콜백함수(이전 반환값, 요소값, 인덱스, 배열), 초기값) : 새로운 배열 반환

배열을 순회하고 콜백함수를 실행하는데 이 전에 나왔던 결과값을 이전 반환값에 해당하는 1번째 인수에 전달함

arr.reduce((이전 반환값, 현재 요소값, 인덱스, 배열)=>이전반환값+현재 요소값,0); // arr 의 합계가 나옴

3.5. some and every

배열을 전부 순회하는데 전달된 콜백함수의 결과값이 한 번이라도 참이면 true 반환함

[1,10,14].some(item=>item>10); //true
[1,10,14].every(item=>item>10); //false

3.6. find and findIndex (ES6)

find : 순회하면서 조건에 맞는 첫번째 요소를 반환함.
findIndex : 순회하면서 조건에 맞는 첫번째 인덱스를 반환함.

profile
무럭무럭

0개의 댓글