■ 비동기 함수 (async function)
비동기 함수란 함수의 내용을 끝까지 쭉 실행하지 않고
중간에 다른 작업을 처리하다가 다시 돌아와서 마무리하는 함수를 뜻한다.
콜백은 비동기 프로그램이에 유용하게 쓰이며
이 두 프로그램의 연관성에 대해 알아보자
비동기 프로그램 - setTimeout 함수
자바스크립트에는 특정 시간이 지난 다음에
어떤 함수를 실행해 주는 setTimeout 이라는 함수가 있으며
다음과 같이 사용한다.
setTimeout(()=> console.log('hello'),3000);
첫 번째 아규먼트로 콜백을 받는 상황에서 setTimeout 함수는 3000ms 이며
3초가 지나면 콜백을 실행해주는 코드이다.
실제로 실행해보면 아무 동작도 없다가 3초 후에 'hello'가 출력되는 것을 확인할 수 있다.
첫 번째 아규먼트로는 어떤 콜백이든 전달할 수 있다고 했을 때
또 다른 예시를 보자면
console.log('1');
setTimeout(()=> console.log('2'),3000);
console.log('3');
보이는 것처럼 1과 3이 먼저 출력 되고
3초 뒤에 2가 출력되는 것을 볼 수 있는데
코드에서는 1,2,3 순서이지만 실제로 실행될 때는 setTimeout 함수 때문에
2는 나중에 실행된다.
이 코드가 바로 비동기 프로그램의 예시라고 볼 수 있다.
그 이유는 코드가 쓰여져 있는 순서대로 실행되지 않기 때문이다.
위 코드의 실행 순서를 그림으로 표현하자면
우선 1이 먼저 실행되고
이후에는 setTimeout 함수가 실행된다.
여기서 지금 시점에 콜백까지 실행한 다음에 다음 줄로 넘어가는 것이 아닌
3초 세는 타이머를 시작하기만 하고 바로 다음 줄로 넘어간다.
그래서 일단 3이 실행되고 3초가 지나면 setTimeout에 전달된 콜백이 실행된다.
이번엔 setTimeout 함수가 코드를 순서대로 실행하는 동기 함수(synchronous function) 였다고 가정하면
이전과 같이 1이 가장 먼저 실행될 것이고 그다음 setTimeout 함수가 실행된다.
타이머를 시작하고 이번엔 3초를 전부 다 기다린 다음에
콜백까지 실행한다.
그리고 마지막으로 3이 실행된다.
두 그래프를 비교해보면
비동기 프로그램이 동기 프로그램보다 조금 더 빨리 끝나는 것을 확인할 수 있는데
차이가 미세해도 setTimeout 이후의 작업이 더 오래걸리는 코드였거나
더 많은 작업이 있었다면 비동기 프로그램이 더더욱 효울적일 것이다.
즉 비동기 프로그램은 오래 걸리는 작업이 있을 때
기다리는 동안 다른 작업을 먼저 처리함으로써 시간을 절약해주는 장점이 있다.
또한 setTimeout 함수를 비동기 함수(async function) 라고 부르며
처음에 설명했다시피 함수의 내용을 끝까지 실행하지 않고
중간에 다른 작업을 처리하다가 다시 돌아와서 마무리하는 함수를 뜻한다.
콜백을 이용하면 나중에 해야하는 작업을 함수 형태로 전달해 줄 수 있기 때문에
비동기 함수를 구현하는데 유용하게 사용되며
콜백이라는 이름에 대해 생각해보면
'Call Back' 나중에 다시 부르다. 라고 볼 수 있으며
바깥 함수 안에서 콜백이 언젠가 다시 불러들여 실행되기 때문에 이러한 이름을 가지고 있는 것이다.
자바스크립트나 자바스크립트 라이브러리는 다양한 비동기 함수를 제공해주기에
개발자는 이런 함수에 콜백을 넘겨 주기만 하면 비동기 프로그램을 구현할 수 있다.
비동기 실행의 특징
▶ 비동기 함수는 이후에 있는 코드를 모두 실행하고 콜백을 실행한다고 했을 때,
console.log('1');
setTimeout(() => console.log('2'), 0);
console.log('3');
console.log('4');
console.log('5');
console.log('6');
console.log('7');
console.log('8');
console.log('9');
console.log('10');
콜백을 바로 실행하기 위해 setTimeout() 함수의 두 번째 파라미터로 0을 넘겼다.
즉 0초이기 때문에 순서대로 출력될 것 같지만
setTimeout 함수 아래 코드들이 먼저 실행되고 콜백이 실행되는 것을 확인할 수 있다.
즉 비동기 함수의 콜백은 아무리 빨리 실행되어도 비동기 함수 이후에 있는 코드가
모두 실행된 후에 실행되기 때문에 위와 같은 결과가 나온 것이다.
반대로 생각하면 비동기 함수 이후에 있는 코드가 굉장히 오래 걸려도
그걸 모두 실행하고 콜백을 실행한다.
▶ 실행할 콜백이 여러 개일 경우 동기적으로 실행된다.
다음 코드를 살펴보면
console.log('1');
setTimeout(() => console.log('2'), 1001);
setTimeout(() => console.log('3'), 1000);
console.log('4');
두 번째 setTimeout() 의 콜백이 실행되는 동안
첫 번째 setTimeout()의 타이머가 끝나는데
이런 경우에 콜백은 동기적으로(순차적으로) 실행된다.
중요한 점은 비동기 작업이 비교적 오래걸리는 작업들이라는 것인데
예를 들면 특정 시간을 기다리거나 사용자의 상호 작용을 기다리는 작업,
웹 리퀘스트의 결과를 기다리는 작업처럼 말이다.
이런 비동기 작업들은 병렬적으로 처리되기 때문에 충분히 효율적은 코드를 작성할 수 있다.
문제 풀이 - setTimeout() 함수
간단하게 문제를 풀어보자
setTimeout() 함수는 2개의 아규먼트를 받을 수 있다.
setTimeout(callback, delay, arg0, arg1, ...);
첫 번째 아규먼트 callback은 실행할 콜백, 두 번째 아규먼트 delay는 timeout 시간(ms 단위),
그 이후의 아규먼트들은 callback의 아규먼트로 전달 된다고 했을 때,
function sayHello(name) {
console.log(`Hello ${name}!`);
}
console.log('시작');
setTimeout()
console.log('끝');
sayHello() 함수를 이용해서 출력 결과를 '시작' '끝' 'Hello 섭이!' 순서로 출력하고
delay는 2초로 설정하려고 한다.
첫 번째 아규먼트는 콜백 sayHello()를 전달하고
두 번째 아규먼트는 2000(ms)를 전달하고
세 번째 아규먼트는 sayHello에 전달할 아규먼트 '섭이'를 전달해야한다면
코드는 다음가 같이 작성할 수 있다.
setTimeout(sayHello, 2000, '섭이');
위 코드를 정답으로 할 수 있지만
화살표 함수를 사용한다면 다음과 같이 적용해볼 수 있다.
setTimeout((name) => {
console.log(`Hello ${name}!`);
}, 2000, '섭이');
조금 더 간결하게 적용해보자
setTimeout(()=> {
sayHello('섭이')
},2000)
정답은 다양하므로 본인이 이해한 만큼 코드를 적용해보자.
'JS' 카테고리의 다른 글
(4) Asynchronous JavaScript - Callback Hell (0) | 2025.01.01 |
---|---|
(3) Asynchronous JavaScript - 비동기 함수들의 예시 (0) | 2024.12.31 |
(1) Asynchronous JavaScript - 비동기 자바스크립트의 콜백(callback) (0) | 2024.12.27 |
(9) JavaScript Module - 유용한 npm 커맨드 (0) | 2024.12.26 |
(8) JavaScript Module - package-lock.json (0) | 2024.12.25 |