상세 컨텐츠

본문 제목

[React.js]2장. 자바스크립트의 실전-구조 분해 할당 ~ 2장. 자바스크립트 실전 - 비동기 처리

25-26/React.js

by jheartit 2025. 10. 10. 10:13

본문

728x90

1. 구조 분해 할당

구조 분해 할당은 말뜻 그대로 구조를 분해해 할당하는 문법입니다.

배열,객체의 구조 분해 할당으로 나눌 수 있습니다. 

1-1. 배열의 구조 분해 할당

  배열의 요소를 순차적으로 추출하여 개별 변수에 할당하는 문법입니다.저장된 요솟값을 변수 선언과 동시에 순서대로 할당합니다.

배열의 길이와 할당할 변수의 개수가 일치하지 않아도 오류가 발생하지 않습니다. 대괄호 속에서 선언한 변수만큼 할당합니다. 

let cities = ['Seoul', 'Busan', 'Jeju'];
let [capital,port,island] = arr;

console.log(capital, port, island); //Seoul Busan Jeju
  •   배열의 길이와 할당할 변수의 개수가 일치 하지 않는 경우
let cities = [Seoul,busan];
let [capital, port, island] = arr;

console.log(capital, port, island); // Seoul busan undefiend

 

-> 배열의 길이를 넘는 변수에는 undefined  할당되기 때문에 조심해야 합니다.

 

1-2 객체의 구조 분해 할당

  객체 속성을 이름으로 추출하여 개별 변수에 쉽게 할당하는 문법 입니다. 중요할 점은 배열과 달리 데이터 저장 순서가 아니라 key를 기준으로 합니다. 함수 func에서는 전달된 객체에서 프로퍼티의 value를 매개변수 name, age, location에 각각 구조 분해 할당합니다. 구조 분해 할당을 하게 된다면 필요한 프로퍼티만 전달할 수 있어 코드가 훨씬 더 유연해집니다. 또한 밑에 코드와 같이 매개변수의 이름을 새롭게 바꿀 수 있고, 변수 이름 옆에 콜론과 함께 새 변수명을 쓰면, 새 이름으로 값이 할당됩니다.

function func({ name: n, age: a, location: l }) {
  console.log(n, a, l);
}

let person = {
  name: "이재현",
  age: 26,
  location: "서울"
};

func(person);

// 이재현 26 서울

 

2. 스프레드 연산자와 rest 매개변수

2.1 스프레드 연산자

  배열,문자열,객체 등과 같이 반복이 가능한 객체의 값을 개별 요소로 분리하는 역할을 합니다.스프레드 연산자를 사용할 때는 '...'로 표기하고, 전개 연산자라고도 부릅니다. 변수 앞에 스프레드 연산자를 붙여 개별 요소로 분리되도록 하고, arrA 뒤에 arrB가 순서대로 붙도록 만든 코드입니다. 또한 객체와 함수를 호출할 때도 스프레드 연산자를 이용한다면 유용합니다. 함수를 호출할 때는 배열 요소를 분리하여 함수의 인수로 전달하는 경우도 있습니다. 

let arrA = [1, 2, 3];
let arrB = [...arrA, 4, 5, 6];

console.log(arrB); // [1, 2, 3, 4, 5, 6]

2.1.1 매개변수에서 구조 분해 할당과 스프레드 연산자의 차이

  구조 분해 할당 과정에서는 함수를 호출할 때 전달하는 인수가 1개이고, 그 값이 객체인 경우입니다. 하지만 스프레드 연산자를 이용한다면 인수를 전달하고자 할때 구조 분해 할당 과정과 달리 여러개로 나뉘어 전달됩니다.인수를 여러개로 나뉘어 전달하고자 하기 때문에 매개변수 또한 여러개 선언해야하는 특징이 있습니다. 

 

2.2  rest 매개변수  

  개별 요소들을 반복 가능한 값인 배열로 묶는 역할을 합니다. 스프레드 연산자와 같이 '...' 문법은 똑같지만 역할은 완전히 반대되는 것이 특징입니다. 또한 나머지 매개변수라고 합니다. 매개변수로 사용할 변수의 이름 앞에 ...을 붙이고, 이 나머지 매개변수는 함수에 전달할 인수들을 순차적으로 배열에 저장합니다. 또한 나머지 매개변수와 다른 매개변수를 같이 사용하고자 한다면, 인수는 순차적으로 왼쪽부터 오른쪽으로 할당되는 것이 특징입니다. 주의할 점은 먼저 선언한 매개변수에 할당된 인수를 제외하고 나머지르 ㄹ모두에 배열에 저장하고, 반드시 매개변수에서 마지막에 선언되어야 합니다. 

function func(param, ...rest) {
  console.log(param);
  console.log(rest);
}

func(1, 2, 3, 4);

 

3. 배열과 메서드

   자바스크립트의 배열은 일반 객체에 기능을 추가해 만든 특수한 객체입니다. 쉽게 다룰 수 있도록 배열 메서드를 제공합니다. 

3.1 요소의 추가 및 삭제 메서드 

  배열 요소를 자유롭게 추가,수정,삭제할 수 있습니다.

3.1.1 push

  배열 맨 끝에 요소를 추가하고 새로운 길이를 반환하는 메서드 입니다. 여러 요소를 추가하려면 콤마로 구분해 전달합니다.마지막 요소를 추가하기 때문에 기존 인덱스는 변함이 없습니다. 무조건 배열 맨 끝에 요소를 추가해야 하기 때문에 중간이나 맨 앞에 요소를 추가하고자 할때는 다른 메서드를 이용해야 합니다.

let fruits = ["apple", "banana", "watermelon"];
const newLength = fruits.push("strawberry", "orange");

console.log(fruits); 
console.log(`새로운 배열의 길이: ${newLength}`);

 

3.1.2 pop

  배열 맨 끝 요소를 제거하고, 제거한 요소를 반환하는 메서드 입니다. 빈 배열에서 pop메서드를 사용하면, 제거할 요소가 없기 때문에 undefined를 반환합니다. pop 메서드도 push  메서드와 비슷하게 마지막 요소를 제거하기 때문에 기존 인덱스에 변함이 없습니다. 

let fruits = ["apple", "banana", "watermelon"];
const newLength = fruits.push();

console.log(fruits); 
console.log(`새로운 배열의 길이: ${newLength}`);

 

3.1.3 shift 

  pop 메서드와 반대로 배열의 맨 앞 요소를 제거하고, 제거한 요소를 반환하는 메서드 입니다. 만약 0번 인덱스 요소를 제거한다면 인덱스가 모두 하나씩 앞 당겨집니다. 

let fruits = ["apple", "banana", "watermelon"];
const removedItem = fruits.shift();

console.log(removedItem); 
console.log(fruits);

 

3.1.4 unshift

  push 메서드와 반대로 배열의 맨 앞에 요소를 추가하고, 새 배열의 길이를 반환하는 메서드 입니다. 배열 맨 앞에 여러 요소를 추가하려면, push와 마찬가지로 요소를 콤마로 구분해 전달하면 됩니다. 만약 새 요소의 인덱스가 0이라면 모든 인덱스는 하나씩 밀립니다.

let fruits = ["apple", "banana", "watermelon"];
const newLength = fruits.unshift("orange");

console.log(fruits);
console.log(`새로운 배열의 길이: ${newLength}`);

 

3.1.5 slice

  마치 가위처럼 기존 배열에서 특정 범위를 잘라 새로운 배열을 반환합니다. 이때 원본 배열은 수정되지 않습니다.잘라내려는 배열의 범위를 지정하는 두 개의 인수를 전달하고, start는 잘라낼 범위의 시작, end는 잘라낼 범위의 끝을 지정하는 인덱스입니다. end로 범위의 끝을 지정한다면 그 범위는 end 인덱스 전까지 입니다. 음숫값을 인덱스로 전달이 가능하고, end없이 start만 음수 인덱스로 전달하면, 배열 맨 끝부터 전달한 음수의 절댓값만큼 잘라낸 새 배열을 반환합니다. 

const arr = [1, 2, 3];
const sliced = arr.slice(0, 2); 

console.log(arr); 
console.log(sliced);

 

3.1.6 conact 

  서로 다른 배열을 이어 붙여 새 배열을 반환하는 메서드입니다. 인수로 배열을 전달한다면 요소를 모두 이어 붙이지만, 객체는 하나의 요소로 인식해 삽입됩니다. 

let arrA = [1, 2];
let arrB = [3, 4];
let arrC = arrA.concat(arrB); 

console.log(arrC);   
console.log(arrA);

 

 

3.2 순회 메서드

  배열을 순회하고자 할때는 반복문을 많이 사용하기 때문에 순회 메서드를 이용해 반복합니다.

3.2.1 forEach

  배열의 모든 요소에 순서대로 접근해 특정 동작을 하는 메서드입니다. 인수로 함수를 요구하는 메서드 이고, 함수 호출 과정에서 인수로 전달되는 함수를 콜백 함수라고 했습니다. forEach 메서드는 배열 요소 각각을 순회하면서, 인수로 전달한 콜백 함수가 정의한 대로 요소를 동작 시킵니다. item(현재 순회하는 배열 요소),idx(item의 인덱스),arr(순회 중인 배열)이라는 3개의 매개변수가 제공됩니다. 콜백함수는 함수 표현식이나 화살표 함수로 간략하게 표현 할 수 있습니다. 배열 arr의 모든 요소에 대해 한 번씩 실행됩니다.

  • 기본 문법
function cb(item, index, array) {
  // 요소에 무언가를 할 수 있습니다.
}

arr.forEach(cb);
  • forEach로 전달되는 콜백 함수
const arr = [1, 2, 3];

arr.forEach((item, idx) => { ①
  console.log(`${idx}번째 요소: ${item}`);
});

 

3.3 탐색 메서드

  배열에서 특정 조건을 만족하는 요소를 찾아내는 행위입니다. 탐색 메서드를 활용한다면 간단하게 배열에서 특정 요소를 검색할 수 있습니다. 

3.3.1 indexOf

  배열에서 찾으려는 요소의 인덱스를 반환하는 메서드 입니다. item은 찾으려는 요솟값, fromIndex는 탐색을 시작할 인덱스 번호입니다. 두번째 인수인 fromIndex는 생략 가능하고, 생략한다면 배열의 0번째 인덱스부터 탐색합니다. 만약 fromIndex의 값을 음수로 지정한다면, 탐색 위치는 배열의 맨 뒤부터 시작합니다. fromIndex의 값이 배열의 길이보다 크거나 같은 경우에도 -1을 반환합니다. indexOf는 비교 연산자(===)로 요소 비교하므로 자료형이 다를 경우 다른 값으로 평가합니다. 또한 객체와 객체 자료형의 값을 탐색 할 수 없습니다. 

arr.indexOf(item, fromIndex);

3.3.2 includes

  배열에 특정 요소가 있는지 판별합니다. indexOf처럼 item과 fromIndex를 인수로 전달하며 사용법도 같습니다. 인수로 전달한 요소가 배열에 존재하면 true,없다면 false를 반환합니다. indexOf는 탐색에 성공한다면 해당 요소의 인덱스 번호를 반환하지만,includes는 불리언 값인 true를 반환합니다. 

arr.includes(item, fromIndex)

3.3.3 findIndex

  indexOf처럼 배열에서 찾으려는 요소의 인덱스 번호를 찾아 반환합니다. 인수로 콜백 함수를 전달하는데 이를 '판별 함수'라고 합니다. 배열에서 이 판별 함수를 만족하는 첫 번째 요소의 인덱스를 반환하고, 없다면 -1을 반환합니다. 판별 함수에는 3개의 매개변수인 현재요소 item, 현재 인덱스 index, 탐색 대상 배열 array들이 제공되고, 이러한 변수들로 판별식을 만듭니다.판별 함수 determine은 배열 arr각 요소에 대해 순차적으로 실행하고, 결과는 불리언형으로 반환합니다. findIndex 메서드가 true를 반환한다면 탐색에 성공한 것이고, 그에 대한 탐색을 멈춥니다. 멈춘 인덱스 번호를 반환합니다. 화살표 함수와 삼항 연산자를 이용하면 코드를 더 간단하게 만들 수 있습니다. 판별 함수를 이용해 배열에서 조건과 일치하는 객체 요소를 찾아낼 수 있습니다. 

arr.findIndex( callback(item, index, array) );

3.3.4 find

  findIndex처럼 인수로 판별 함수를 전달하고,배열에서 만족하는 요소를 찾습니다. 하지만 findIndex와 달리 인덱스가 아닌 요소를 반환하는 것이 특징입니다. 또한 배열에서 특정 조건을 만족하는 요소를 찾을 때 유용하게 사용합니다. 

let arr = [
  { name: "서다민",
  { name: "김보경",
  { name: "최현수",
  { name: "이영웅" }
];

let element = arr.find((item) => item.name === "서다민"); 
console.log(element); // {name: "서다민"}

3.3.5 filter

  배열에서 조건을 만족하는 요소만 모아 새로운 배열로 반환하는 메서드입니다. 문법은 find,findIndex와 비슷한것이 특징입니다.

let arr = [
  { name: "지도연", hobby: "독서" },
  { name: "전진호", hobby: "수영" },
  { name: "이다연", hobby: "농구" },
  { name: "육호빈", hobby: "영화" }
];

let filteredArr = arr.filter(
  (item) => item.hobby === "독서"
);

console.log(filteredArr);

 

3.4 탐색 메서드

3.4.1 map

  배열 각각의 요소에 대한 함수 호출 결과를 모아 새 배열을 만들어 반환하는 메서드입니다. 콜백 함수를 인수로 전달하고, item,index,map메서드를 호출한 배열 arr이 매개변수로 제공됩니다. 배열의 모든 요소에 대해 콜백 함수를 실행합니다. 또한 이러한 배열을 새로운 형태로 바꿀 수 있기 때문에 활용도가 매우 높은 메서드 입니다. 

arr.map( callback(item, index, array) );

3.4.2 sort

  배열의 요소를 정렬할 때 사용하는 메서드입니다. 하나의 콜백 함수를 인수로 전달하고, 이 함수는 비교 함수로 사용되고, 필수 사항은 아닙니다. 만약 비교 함수를 생략한다면 사전 순,오름차순으로 정렬합니다. 이 메서드는 새로운 배열을 반환하는 것이 아니라, 기존의 배열 자체를 정렬하는 것입니다. 만약 이 메서드가 요소를 문자열로 취급해 사전순으로 정렬한다면 비교함수가 필요합니다. 비교함수는 배열 요소 두개를 인수로 전달하는데, 함수의 반환값에 따라 정렬방식이 달라지는것이 포인트입니다.

  비교 함수가 양수를 반환한다면 a와 b 중 b의 위치가 a보다 앞이어야 한다는 것을 의미하고, 비교 함수가 음수를 반환한다면 a와 b 중 a의 위치가 b보다 앞이어야 한다는 것을 의미 하고, 비교 함수가 0을 반환한다면 a와 b는 정렬 순서가 동일하다는것을 의미합니다.배열의 모든 요소에 대해 비교 함수를 실행한다면 배열은 오름차순으로 정렬되고, 대부분의 정렬을 수행합니다. 

arr.sort( compare( a, b ) )

3.4.3 join

  배열 요소를 모두 연결해 하나의 문자열로 반환합니다. 분리 기호로 사용하는 구분자(separator)를 인수로 전달하는데 필수 사항은 아닙니다. 구분자는 배열 요소를 합칠 때 각각의 요소를 구분하는 문자열이고, 요소를 구분하고자 할때는 콤마를 통해 구분합니다. 또한 구분자"-"를 각 요소를 구분하기 위해 사용하기도 합니다.

arr.join( separator )

3.4.4 reduce

  배열 요소를 모두 순회하면서 인수로 제공한 함수를 실행하고, 단 하나의 결괏값만 반환하는 메서드입니다. map은 여러개의 결과를 반환할 수 있지만 오로지 reduce는 단 하나의 결과만을 반환한다는 점에서 차이가 있습니다. 호출할 때 2개의 인수를 전달하고, 첫번째 인수는 콜백 함수를 전달하며, 두 번째 인수는 초깃값을 전달합니다.

  reduce 메서드의 첫 번째 인수로 전달하는 콜백함수는 '리듀서'라고 부릅니다. 리듀서는 map,forEach 메서드가 전달하는 콜백 함수처럼 배열의 모든 요소에 대해 각각 실행되고 4개의 매개변수를 받습니다. 

  4개의 매개변수

-acc:누산기,이전 함수의 호출 결과 저장,두번째 인수 초깃값이 acc의 초깃값이 됩니다

-item:현재의 배열 요소,-index: 현재의 배열 인덱스 ,-array: reduce 메서드를 호출한 배열

  acc의 초깃값인 인수 initial은 필수 사항은 아니지만 전달하지 않는다면 배열의 첫 번째 요소인 acc의 초깃값이 됩니다.

  이 메서드를 이용한다면 코드 한 줄로 배열 모든 요소의 누적값을 구할 수 있습니다. 

arr.reduce( ( acc, item, index, array ) => {
  (...)
}, initial );

  

 

4. Date 객체와 날짜

4.1 Date 객체 생성 및 협정 세계시(UTC)

  new 키워드로 Date()를 생성합니다. 아무런 인수도 전달하지 않는다면 생성 당시의 시간,날짜등이 저장된 객체를 반환합니다.

  협정 세계시라고 부르는 UTC(Universial Time Coordinated)를 기준으로 동작합니다. 협정 세계시의 기준인 1970년 1월 1일 0시 0분 0초 인 이 시간을 기준으로 시간과 날짜들을 표현합니다. UTC+0시라고 표현합니다. 특정 시간을 기준으로 수정하고 저장하는 기능인 타임 스탬프를 통해 UTC+0시 기준으로 후의 시간을 Date 객체로 생성해 반환합니다.

let Jan01_1970 = new Date(0);
console.log(Jan01_1970);

// Thu Jan 01 1970 09:00:00 GMT+0900 (한국 표준시)

 

4.2 타임 스탬프

  특정 시간을 기준으로 수정하고 저장하고, 특정 시간이  UTC+0시인 1970년 첫날을 기준으로 흘러간 밀리초(ms)의 시간을 의미합니다. 타임 스탬프를 인수로 전달 가능하고, UTC+0시부터 인수로 전달된 타임 스탬프 이후의 시간 정보를 갖는 Date 객체를 반환합니다.또한 역으로 타임 스탬프를 구할 수도 있습니다.

4.3 원하는 날짜로 Date 객체를 생성

4.3.1 문자열로 특정 날짜 전달하기

 Date 객체 생성자에 문자열로 표현된 날짜를 인수로 전달하면, 해당 날짜를 기준으로 Date 객체를 만들어 반환합니다.

let date1 = new Date("2000-10-10/00:00:00"); 
let date2 = new Date("2000.10.10/00:00:00"); 
let date3 = new Date("2000/10/10/00:00:00"); 
let date4 = new Date("2000 10 10/00:00:00"); 

console.log("1:", date1); // 1: Tue Oct 10 2000 00:00:00 GMT+0900 (한국 표준시)
console.log("2:", date2); // 2: Tue Oct 10 2000 00:00:00 GMT+0900 (한국 표준시)
console.log("3:", date3); // 3: Tue Oct 10 2000 00:00:00 GMT+0900 (한국 표준시)
console.log("4:", date4); // 4: Tue Oct 10 2000 00:00:00 GMT+0900 (한국 표준시)

  

4.3.2 숫자로 특정 날짜 전달하기

  밀리초가 아니라 year, month, date, hours, minutes, seconds, milliseconds 순서로, 날짜와 시간에 해당하는 숫자를 전달해 원하는 Date 객체를 생성합니다.

let date1 = new Date(2000, 10, 10, 0, 0, 0, 0);
let date2 = new Date(2000, 9, 10);

console.log("1:", date1); // 1: Fri Nov 10 2000 00:00:00 GMT+0900 (한국 표준시)
console.log("2:", date2); // 2: Tue Oct 10 2000 00:00:00 GMT+0900 (한국 표준시)

4.3.3 타임 스탬프로 특정 날짜 전달하기

  타임 스탬프는 숫자로 표현 되어 있어 문자열,객체보다 저장 공간을 들 차지하고, 비교와 탐색이 빠릅니다.database에서 날짜와 시간을 저장할 때는 타임스탬프로 저장합니다.

let date = new Date(2000, 9, 10);
let timeStamp = date.getTime(); // 
console.log(timeStamp); // 971103600000

let dateClone = new Date(timeStamp); // 
console.log(dateClone); // Tue Oct 10 2000 00:00:00 GMT+0900 (한국 표준시)

4.4.1Date 객체에서 날짜 요소 얻기

  • getFullYear: 연도 반환
  • getMonth: 월(月) 반환
  • getDate: 일(日) 반환
  • getDay: 요일 반환(0-일요일,6-토요일)
  • getHours, getMinutes, getSeconds, getMilliseconds : 시간,분,초,밀리초 반환

4.4.2 Date 객체에서 날짜 요소 수정하기

  • setFullYear:연도 수정
  • setMonth: 월 수정
  • setDate: 일 수정
  • setHours, setMinutes, setSeconds: 시,분,초 수정

4.4.3 Date 객체 출력하기

  • toString: 현재 저장된 시간을 문자열로 반환(동일한 형태의 문자열 얻기 가능)
  • toDateString: 현재의 날짜만 출력(시간 제외)
  • toLocaleString, toLocaleDateString: 현지화된 날짜와 시간 반환

5. 비동기 처리

  오래 걸리는 작업이 종료될 때까지 기다리지 않고 다음 작업을 수행하는 기능이 있습니다. 자바스크립트는 순차적인 기능이 기본적으로 탑재되어 있습니다.이러한 순차적으로 코드를 실행하는것을 동기(Synchronous) 라고 합니다. 동기는 은행 창구 시스템에 비유할 수 있습니다. 한 은행원이 한 고객만 응대할 수 있는 예시입니다. 하지만 이러한 것을 계속 하다보면 지연 문제가 생기기 마련입니다. 이러한 문제를 해결하기 위하여 비동기(asynchronous) 처리를 하는것이 좋습니다.

  비동기란 특정 작업을 다른 작업과 관계없이 독립적으로 동작하게 만드는 것입니다. 함수 setTimeout을 이용하면 작업을 비동기 적으로 처리할 수 있고, 화살표를 이용하여 도 간결하게 작성 할 수 있습니다. 비동기는 카페에 비유가 가능합니다. 종업원은 여러개의 주문을 한번에 받고, 고객은 앞서 주문한 음료가 모두 제조되기까지 기다렸다 주문할 필요가 없습니다. 비동기는 동기 작업과 달리 작업의 실행 순서와 완료 순서가 일치하지 않습니다.

5.1 콜백 함수로 비동기 처리하기

  setTimeout은 내장 함수이고, 콜백함수는 함수 setTimeout에서 전달하는 인수입니다. 콜백 함수를 이용하면 비동기 작업의 결괏값을 사용할 수 있습니다. 

function double(num, cb) {
  setTimeout(() => {
    const doubleNum = num * 2;
    cb(doubleNum); // 
  }, 1000);
}

double(10, (res) => {  // 
  console.log(res);
});

console.log("마지막"); // 

// 마지막
// 20

5.2 프로미스 객체를 이용해 비동기 처리하기

  프로미스란 비동기 처리 목적으로 제공되는 자바스크립트 내장 객체입니다. 특수한 목적을 위해 다양하게 기능이 추가된 객체이고, 프로미스를 사용하는것이 콜백함수 보다 더 쉽게 작업을 수행할 수 있습니다.

  프로미스는 진행 단계에 따라 3가지 상태로 나뉘는데, 대기(Pending) 상태/ 성공(Fulfilled) 상태/ 실패(Rejected) 상태 로 나뉩니다. 대기 상태에서 작업이 완료가 되었다면 해결(resolve)을 했다라고 하고, 대기 상태에서 오류 발생과 같은 문제가 발생해 실패하게 된다면 거부(reject)가 되었다고 합니다. 

  실행 함수가 제공받는 매개변수는 2가지인 resolve(비동기 작업의 상태를 성공으로 바꾸는 함수)와 reject(비동기 작업의 상태를 실패로 바꾸는 함수)가 있습니다.

const promise = new Promise(실행 함수);

출처: 이정환, 『한 입 크기로 잘라먹는 리액트』, 프로그래밍인사이트(2023), p88-

Corner React.js
Editor: Dori

728x90

관련글 더보기