동기/비동기 처리
동기적(Synchronous) 처리
- 코드는 기본적으로 작성한 순서대로 위에서부터 아래로 순차적으로 실행됩니다. 즉, 한번에 코드 한줄씩 차례차례 실행된다는 소리입니다.
- 요청을 하면 결과가 주어질 때까지 다른 요청이 처리되지 않으며, 해당 요청 결과가 처리된 후 다음 순서에 맞춰 진행됩니다.
- 자바스크립트를 실행하는 웹브라우저는 stack이라는 코드 실행 공간이 있는데 거기서 코드를 한줄한줄 차례로 실행합니다.
예를 들어, 아래와 같은 코드가 있다면 어떤 순서대로 출력될까요?
console.log(1);
console.log(2);
console.log(3);
예상하신 대로 1,2,3이 차례대로 출력됩니다.
왜냐면 자바스크립트는 한번에 코드 한줄씩 차례차례 실행하니까요. 이걸 전문용어로 동기적이다 (synchronous) 라고 합니다.
비동기적(Asynchronous) 처리
- 요청에 대한 응답이 즉시 처리되지 않아도, 그 대기 시간 동안 다른 요청을 보낼 수 있습니다.
- 요청이 진행되더라도 응답을 기다리지 않고 다음 코드가 수행됩니다.
- 비동기로 실행된 요청은 콜백 함수를 통해 응답을 처리할 수 있습니다.
특정 코드를 1초 후에 실행하고 싶으면 어떻게하죠?
예를 들어, 자바스크립트에서 1초 쉬고 뭔가 출력하는 코드를 작성하려면
console.log(1);
setTimeout(function(){}, 1000);
console.log(2);
이런식으로 작성하면될까요?
안됩니다. 1과 2가 콘솔창에 동시에 출력됩니다.
왜그러냐면 setTimeout() 이라는 함수를 잘 보시면 이건 실행까지 시간이 조금 걸리는 함수죠? 1초나 걸립니다.
자바스크립트 실행머신인 웹브라우저는 이런 특수한 코드들을 발견하면 약간 제쳐두고 다른 코드부터 실행하려고 합니다. 그래서 setTimeout() 을 제껴두고 그 밑에 있는 console.log(2)라는 코드 부터 실행하는 것입니다.
이런 처리방식을 바로 비동기(asynchronous)라고 합니다.
실행이 오래걸리는 그런 코드들은 잠깐 대기실에 제쳐두고, 실행이 바로바로 가능한 코드들부터 처리하는 방식을 뜻합니다.
이건 자바스크립트 언어 자체의 기능이 아니라 자바스크립트 실행을 도와주는 웹브라우저 덕분에 해낼 수 있는 것입니다.
잠깐 코드를 제쳐두는 대기실
실행을 미루고 옆으로 잠깐 제껴둘 수 있는 코드들은 미리 정해져있습니다.
위에서 말했던 setTimeout, addEventListener, ajax 관련 함수들이 바로 그것입니다.
setTimeout, addEventListener, ajax관련 함수들은 1초대기, 클릭대기 이런걸 하는 코드들인데 이런 코드들의 특징은.. 읽는 시점과 동작 시점이 차이가 있습니다. (쉽게 말하면 동작까지 오래걸립니다.)
자바스크립트를 실행하고 해석하는 크롬쨩은 이런 특별한 코드들을 만나면
1. 잠깐 대기실에 제껴두고 2. 준비가 완료되면 다시 실행시킵니다.
console.log(1);
setTimeout(function(){}, 1000);
console.log(2);
▲ 웹브라우저는 위의 코드를 읽다가 setTimeout 이런 코드를 만나면 잠시 Web API 대기실로 옮겨서 대기시킵니다.
그리고 1초의 대기시간이 지나고 setTimeout이 완료가 되면 대기실에서 코드를 꺼내서 코드가 실행되게 만들어줍니다.
이것 덕분에 setTimeout같이 시간이 오래걸리는 코드들을 비동기식으로 처리할 수 있는 것입니다.
그래서 자바스크립트는 평소에 별일 없으면 동기식으로 처리하는데 비동기를 지원하는 setTimeout 같은 함수를 이용하면 비동기식으로 동작하게 만들 수 있는 언어입니다.
콜백 함수(callback)
콜백함수란? 함수의 전달인자로 다른 함수에 전달되는 함수입니다.
콜백함수를 호출하는 방법에는 "synchronous" 및 "asynchronous" 두 가지가 있습니다.
- 동기식 콜백(synchronous callbacks)은 중간에 비동기 작업 없이 외부 함수 호출 직후에 호출
- 비동기식 콜백(asynchronous callbacks)은 asynchronous 작업이 완료된 후 나중에 호출됩니다.
콜백 함수가 동기식으로 호출되는지, 비동기식으로 호출되는지 이해하는 것은 부수 효과를 분석할 때 특히 중요합니다.
let value = 1;
doSomething(() => {
value = 2;
});
console.log(value);
doSomething이 동기식으로 콜백을 호출하는 경우,
value = 2가 동기식으로 실행되기 때문에 마지막 코드 실행문(console.log 문)은 2를 기록합니다.
그렇지 않고,
콜백 함수가 비동기인 경우 value = 2가 console.log 문 다음에 실행되기 때문에 마지막 코드 실행문(console.log 문)은 1를 기록합니다.
동기식 콜백(synchronous callbacks)의 예는 Array.prototype.map(), Array.prototype.forEach()에 전달된 콜백 함수가 포함됩니다.
비동기식 콜백(asynchronous callbacks)은 setTimeout() 및 Promise.prototype.then()에 전달된 콜백 함수들을 예제가 될 수 있습니다.
출처 : Mdn
https://developer.mozilla.org/ko/docs/Glossary/Callback_function
콜백함수 디자인하는 법
순차적으로 실행하고 싶은 함수가 두개 있다고 칩시다. 그럼 이렇게 코드짜면 될까요?
function 첫째함수(){
console.log(1)
}
function 둘째함수(){
console.log(2)
}
첫째함수();
둘째함수();
자바스크립트는 비동기라는 특수성으로 인해 이렇게 쓴다고 순차적으로 실행하는걸 보장하진 않습니다.
(첫째함수가 뭐 setTimeout이라든지 Web API 대기실로 보내는 코드라면 나중에 실행될 수 있으니까요)
콜백함수를 만들어서 첫째함수(둘째함수);
이런 식으로 실행시킬 수 있게 만들어놓으면 순차적으로 실행할 수 있겠죠?
그럼 어떻게 코드를 짜놔야 함수를 함수안에 집어넣을 수 있을까요?
function 첫째함수(콜백){
console.log(1);
콜백();
}
function 둘째함수(){
console.log(2)
}
첫째함수(둘째함수);
함수에 파라미터를 하나 뚫어주시면 됩니다.
그리고 그 파라미터에 소괄호를 붙여서 실행해주세요~ 라고 하면 함수안에 함수를 집어넣어서 실행이 가능합니다.
이게 콜백함수 디자인하는 법입니다.
위처럼 미리 만들어놓은 함수를 집어넣을 수도 있고
첫째함수(function(){
console.log(2)
}):
이렇게 직접 함수선언문을 집어넣을 수도 있습니다.
순차적으로 실행하려고 콜백함수를 여러개 사용하면 단점이 조금 있습니다.
코드가 옆으로 길어집니다.
첫째함수(function(){
둘째함수(function(){
셋째함수(function(){
어쩌구..
});
});
}):
첫째함수 둘째함수 셋째함수 이렇게 차례로 실행해주는 코드입니다.
이런식으로 옆으로 길어지는 콜백함수를 콜백지옥이라고도 합니다.
이런 콜백지옥을 경험하기 싫으시면 ES6 신문법인 Promise라는 기계를 만들어 사용하시면 됩니다.
쉽게 이해하고 싶으면 해당 영상을 참고해주세요.
(참고) 별코딩 : 자바스크립트 - Callback functions 콜백함수란?
'Javascript' 카테고리의 다른 글
자바스크립트 JavaScript : async/await (0) | 2024.04.03 |
---|---|
자바스크립트 JavaScript : Promise (0) | 2024.04.03 |
자바스크립트 Javascript : Destructuring 문법 (0) | 2024.04.03 |
자바스크립트 JavaScript : getter / setter (0) | 2024.04.02 |
자바스크립트 Javascript : Class 상속기능 (0) | 2024.04.02 |
동기/비동기 처리
동기적(Synchronous) 처리
- 코드는 기본적으로 작성한 순서대로 위에서부터 아래로 순차적으로 실행됩니다. 즉, 한번에 코드 한줄씩 차례차례 실행된다는 소리입니다.
- 요청을 하면 결과가 주어질 때까지 다른 요청이 처리되지 않으며, 해당 요청 결과가 처리된 후 다음 순서에 맞춰 진행됩니다.
- 자바스크립트를 실행하는 웹브라우저는 stack이라는 코드 실행 공간이 있는데 거기서 코드를 한줄한줄 차례로 실행합니다.
예를 들어, 아래와 같은 코드가 있다면 어떤 순서대로 출력될까요?
console.log(1);
console.log(2);
console.log(3);
예상하신 대로 1,2,3이 차례대로 출력됩니다.
왜냐면 자바스크립트는 한번에 코드 한줄씩 차례차례 실행하니까요. 이걸 전문용어로 동기적이다 (synchronous) 라고 합니다.
비동기적(Asynchronous) 처리
- 요청에 대한 응답이 즉시 처리되지 않아도, 그 대기 시간 동안 다른 요청을 보낼 수 있습니다.
- 요청이 진행되더라도 응답을 기다리지 않고 다음 코드가 수행됩니다.
- 비동기로 실행된 요청은 콜백 함수를 통해 응답을 처리할 수 있습니다.
특정 코드를 1초 후에 실행하고 싶으면 어떻게하죠?
예를 들어, 자바스크립트에서 1초 쉬고 뭔가 출력하는 코드를 작성하려면
console.log(1);
setTimeout(function(){}, 1000);
console.log(2);
이런식으로 작성하면될까요?
안됩니다. 1과 2가 콘솔창에 동시에 출력됩니다.
왜그러냐면 setTimeout() 이라는 함수를 잘 보시면 이건 실행까지 시간이 조금 걸리는 함수죠? 1초나 걸립니다.
자바스크립트 실행머신인 웹브라우저는 이런 특수한 코드들을 발견하면 약간 제쳐두고 다른 코드부터 실행하려고 합니다. 그래서 setTimeout() 을 제껴두고 그 밑에 있는 console.log(2)라는 코드 부터 실행하는 것입니다.
이런 처리방식을 바로 비동기(asynchronous)라고 합니다.
실행이 오래걸리는 그런 코드들은 잠깐 대기실에 제쳐두고, 실행이 바로바로 가능한 코드들부터 처리하는 방식을 뜻합니다.
이건 자바스크립트 언어 자체의 기능이 아니라 자바스크립트 실행을 도와주는 웹브라우저 덕분에 해낼 수 있는 것입니다.
잠깐 코드를 제쳐두는 대기실
실행을 미루고 옆으로 잠깐 제껴둘 수 있는 코드들은 미리 정해져있습니다.
위에서 말했던 setTimeout, addEventListener, ajax 관련 함수들이 바로 그것입니다.
setTimeout, addEventListener, ajax관련 함수들은 1초대기, 클릭대기 이런걸 하는 코드들인데 이런 코드들의 특징은.. 읽는 시점과 동작 시점이 차이가 있습니다. (쉽게 말하면 동작까지 오래걸립니다.)
자바스크립트를 실행하고 해석하는 크롬쨩은 이런 특별한 코드들을 만나면
1. 잠깐 대기실에 제껴두고 2. 준비가 완료되면 다시 실행시킵니다.
console.log(1);
setTimeout(function(){}, 1000);
console.log(2);
▲ 웹브라우저는 위의 코드를 읽다가 setTimeout 이런 코드를 만나면 잠시 Web API 대기실로 옮겨서 대기시킵니다.
그리고 1초의 대기시간이 지나고 setTimeout이 완료가 되면 대기실에서 코드를 꺼내서 코드가 실행되게 만들어줍니다.
이것 덕분에 setTimeout같이 시간이 오래걸리는 코드들을 비동기식으로 처리할 수 있는 것입니다.
그래서 자바스크립트는 평소에 별일 없으면 동기식으로 처리하는데 비동기를 지원하는 setTimeout 같은 함수를 이용하면 비동기식으로 동작하게 만들 수 있는 언어입니다.
콜백 함수(callback)
콜백함수란? 함수의 전달인자로 다른 함수에 전달되는 함수입니다.
콜백함수를 호출하는 방법에는 "synchronous" 및 "asynchronous" 두 가지가 있습니다.
- 동기식 콜백(synchronous callbacks)은 중간에 비동기 작업 없이 외부 함수 호출 직후에 호출
- 비동기식 콜백(asynchronous callbacks)은 asynchronous 작업이 완료된 후 나중에 호출됩니다.
콜백 함수가 동기식으로 호출되는지, 비동기식으로 호출되는지 이해하는 것은 부수 효과를 분석할 때 특히 중요합니다.
let value = 1;
doSomething(() => {
value = 2;
});
console.log(value);
doSomething이 동기식으로 콜백을 호출하는 경우,
value = 2가 동기식으로 실행되기 때문에 마지막 코드 실행문(console.log 문)은 2를 기록합니다.
그렇지 않고,
콜백 함수가 비동기인 경우 value = 2가 console.log 문 다음에 실행되기 때문에 마지막 코드 실행문(console.log 문)은 1를 기록합니다.
동기식 콜백(synchronous callbacks)의 예는 Array.prototype.map(), Array.prototype.forEach()에 전달된 콜백 함수가 포함됩니다.
비동기식 콜백(asynchronous callbacks)은 setTimeout() 및 Promise.prototype.then()에 전달된 콜백 함수들을 예제가 될 수 있습니다.
출처 : Mdn
https://developer.mozilla.org/ko/docs/Glossary/Callback_function
콜백함수 디자인하는 법
순차적으로 실행하고 싶은 함수가 두개 있다고 칩시다. 그럼 이렇게 코드짜면 될까요?
function 첫째함수(){
console.log(1)
}
function 둘째함수(){
console.log(2)
}
첫째함수();
둘째함수();
자바스크립트는 비동기라는 특수성으로 인해 이렇게 쓴다고 순차적으로 실행하는걸 보장하진 않습니다.
(첫째함수가 뭐 setTimeout이라든지 Web API 대기실로 보내는 코드라면 나중에 실행될 수 있으니까요)
콜백함수를 만들어서 첫째함수(둘째함수);
이런 식으로 실행시킬 수 있게 만들어놓으면 순차적으로 실행할 수 있겠죠?
그럼 어떻게 코드를 짜놔야 함수를 함수안에 집어넣을 수 있을까요?
function 첫째함수(콜백){
console.log(1);
콜백();
}
function 둘째함수(){
console.log(2)
}
첫째함수(둘째함수);
함수에 파라미터를 하나 뚫어주시면 됩니다.
그리고 그 파라미터에 소괄호를 붙여서 실행해주세요~ 라고 하면 함수안에 함수를 집어넣어서 실행이 가능합니다.
이게 콜백함수 디자인하는 법입니다.
위처럼 미리 만들어놓은 함수를 집어넣을 수도 있고
첫째함수(function(){
console.log(2)
}):
이렇게 직접 함수선언문을 집어넣을 수도 있습니다.
순차적으로 실행하려고 콜백함수를 여러개 사용하면 단점이 조금 있습니다.
코드가 옆으로 길어집니다.
첫째함수(function(){
둘째함수(function(){
셋째함수(function(){
어쩌구..
});
});
}):
첫째함수 둘째함수 셋째함수 이렇게 차례로 실행해주는 코드입니다.
이런식으로 옆으로 길어지는 콜백함수를 콜백지옥이라고도 합니다.
이런 콜백지옥을 경험하기 싫으시면 ES6 신문법인 Promise라는 기계를 만들어 사용하시면 됩니다.
쉽게 이해하고 싶으면 해당 영상을 참고해주세요.
(참고) 별코딩 : 자바스크립트 - Callback functions 콜백함수란?
'Javascript' 카테고리의 다른 글
자바스크립트 JavaScript : async/await (0) | 2024.04.03 |
---|---|
자바스크립트 JavaScript : Promise (0) | 2024.04.03 |
자바스크립트 Javascript : Destructuring 문법 (0) | 2024.04.03 |
자바스크립트 JavaScript : getter / setter (0) | 2024.04.02 |
자바스크립트 Javascript : Class 상속기능 (0) | 2024.04.02 |