반응형
동기(Sync) & 비동기(Async)
- 동기(Sync)와 비동기(Async)에 대한 개념
- 일반적으로 "동기로 실행된다" 라고 함은, 먼저 실행된 코드의 결과가 나올때까지 대기하는것을 말합니다.
- 놀이기구를 생각하면 쉽습니다. 정원이 30명인 놀이기구가 있다고 가정합니다. 놀이기구를 한번 태우는데 약 5분이 걸린다고 가정하면 놀이기구를 막 태우기 시작한 시점에서는 대기자 모두 5분이 지나 이미 놀이기구에 탑승했던 사람들이 다 내리기 전까지는 탑승을 할 수 없습니다. 이것은 놀이기구 탑승/하차가 동기적으로 관리된다고 볼 수 있습니다.
- 일반적으로 "비동기로 실행된다" 라고 함은, 실행된 순서와 관계 없이 결과가 나오는것을 말합니다.
- 맛집을 생각하면 쉽습니다. 정원이 최대 30명인 맛집이 있다고 가정합니다. 입장 순서는 선착순이고 퇴장 순서는 다 먹은 사람이 바로 나올 수 있습니다. 다 먹은 사람이 나오면 나온 사람 수 만큼 다시 입장 할 수 있습니다. 사람마다 먹는 시간은 모두 다릅니다. 이것은 입/퇴장이 비동기적으로 처리된다고 볼 수 있습니다.
- 일반적으로 "동기로 실행된다" 라고 함은, 먼저 실행된 코드의 결과가 나올때까지 대기하는것을 말합니다.
- Blocking Model & Non-Blocking Model
- Blocking Model이란, 코드의 실행이 끝나기 전까지 실행 제어권을 다른곳에 넘기지 않아 다른 작업을 하지 못하고 대기하는 것을 말합니다.
- Non-Blocking Model이란, 코드의 실행이 끝나지 않아도 실행 제어권을 다른곳에 넘겨 다음 코드가 실행될 수 있는것을 말합니다.
- 자바스크립트는 Async + Non-Blocking Model을 채용하여 현재 실행중인 코드의 실행이 끝나지 않아도 다음 코드를 호출합니다.
- 결론적으로 자바스크립트는 각 명령들이 순서대로 실행될 수 있게 구현되어 있지만, Non-Blocking Model에 의해 동기적 명령이 아닌 모든 함수는 비동기적으로 실행됩니다.
- ❓ 동기, 비동기와 뭐가 다른걸까?
- 제어권을 넘기면(Non-blocking) 다른 코드도 실행될 수 있으므로 비동기 처리가 가능하지만
- 제어권을 넘기지 않으면(Blocking) 비동기 처리가 가능한 환경이어도 비동기 처리가 불가능합니다.
동기(Sync) Promise
- 자바스크립트에서 비동기 처리를 동기로 처리할 수 있게 돕는 Built-in(미리 내부적으로 정의된)객체 유형입니다. 이 객체를 이용하면 여러분은 비동기 처리를 아주 손쉽게 할 수 있습니다.
- Promise 생성자 인터페이스 executor에는 함수만 올 수 있으며 인자로 resolve, reject가 주입됩니다.
- executor는 Promise의 실행 함수라고 불리고, Promise가 만들어질 때 자동으로 실행됩니다. Promise가 연산을 언제 종료하는지 상관하지 않고, resolve, reject 중 하나를 무조건 호출해야합니다.
new Promise(executor);
// 예제
new Promise((resolve, reject) => {
// 명령문
});
Promise는 반드시 3가지 상태를 지니며, 대기(Pending) 상태가 아니라면 Promise의 연산이 이미 끝난 상태로 볼 수 있습니다.
- Promise의 상태
- 대기(Pending): 이행하거나 거부되지 않은 초기 상태.
- 이행(Fulfilled): 연산이 성공적으로 완료됨.
- 거부(Rejected): 연산이 실패함.
- Promise가 만들어 질 때 executor가 실행되며, executor에서 resolve 함수가 호출되기 전까지 firstPromise.then(...) 안에 있는 코드를 실행하지 않습니다.
Promise 안에서 resolve가 실행 된 경우 then 메서드에 작성된 함수가 실행됩니다.
const resolvePromise = new Promise((resolve, reject) => {
setTimeout(() => {
console.log('First');
resolve('Resolve!'); // resolve를 실행할 때, 안에 데이터를 넣어줄 수 있습니다.
}, 1000);
});
resolvePromise.then((data) => {
console.log('Middle');
console.log('Last');
console.log(data);
})
// Print: First -> 1초 뒤에 출력됩니다.
// Middle
// Last
// Resolve!
- Promise.catch
- Promise 안에서 에러가 throw 되거나 reject가 실행되면 catch 메서드에 작성한 함수가 실행됩니다.
const errorPromise = new Promise((resolve, reject) => {
setTimeout(() => {
console.log('First');
reject('Error!!'); // 직접 reject를 실행하면 프로미스에서 에러가 발생한것으로 간주됩니다.
}, 1000);
});
errorPromise.then(() => {
console.log('Middle');
console.log('Last');
}).catch((error) => {
console.log('에러 발생!', error);
});
// Print: First -> 1초 뒤에 출력됩니다.
// 에러 발생!, Error!!
const countPromise = Promise.resolve(0);
function increment(value) {
return value + 1;
}
const resultPromise = countPromise.then(increment).then(increment).then(increment);
resultPromise.then(console.log);
// Print: 3
비동기(Async)
- 특징
- 비동기 함수의 결과 값은 항상 Promise 객체로 resolve된다.
- 비동기 함수 안에서만 await 연산자를 사용할 수 있다. (바로 아래에서 배웁니다!)
- 비동기 함수는 일반 함수나 화살표 함수와 아주 비슷하지만 딱 두가지만 다릅니다.
await 연산자
- await 연산자를 사용하면 Promise가 fulfill 상태가 되거나 rejected될 때 까지 함수의 실행을 중단하고 기다릴 수 있습니다. Promise의 연산이 끝나면 함수에서 반환한 값을 얻을 수 있습니다.
- await 연산자는 async 함수 안에서만 사용할 수 있습니다.
function 시간(time) {
return new Promise((resolve, reject) => {
setTimeout(() => {
console.log(time, '에 해당하는 시간이 지났습니다.')
resolve();
}, time);
})
}
async function 호출() {
console.log('시작 되었습니다.')
시간(1000)
console.log('종료 되었습니다.')
}
호출();
// Print: 시작 되었습니다.
// 종료 되었습니다.
// 1000에 해당하는 시간이 지났습니다.
await 연산자의 활용
function 시간(time) {
return new Promise((resolve, reject) => {
setTimeout(() => {
console.log(time, '에 해당하는 시간이 지났습니다.')
resolve();
}, time);
})
}
async function 호출() {
console.log('시작 되었습니다.')
await 시간(1000)
console.log('종료 되었습니다.')
}
호출();
// Print: 시작 되었습니다.
// 1000에 해당하는 시간이 지났습니다.
// 종료 되었습니다.
위와 같이 await 연산자를 활용해 동기 처리를 해줄 수 있습니다.
반응형
'JavaScript&TypeScript' 카테고리의 다른 글
JavaScript 클래스를 알아보자 class (0) | 2022.12.12 |
---|---|
JavaScript Error handling 에러 핸들 (0) | 2022.12.12 |
JavaScript 고급 함수 forEach() (1) | 2022.12.10 |
JavaScript 클래스와 객체 함수의 차이? (0) | 2022.11.22 |
Form 태그 새로고침 막는법 (0) | 2022.11.19 |
댓글