자바스크립트의 sync / async
자바스크립트는 일방적으로 동기방식이다. 윗줄부터 차례로 코드가 실행 된다.
하지만 sync / async 함수를 사용하면 비동기적으로 코드실행이 가능하다.
순차적 실행이 아닌, 완료되면 실행이 된다.
(ajax, 이벤트리스너, setTimeout 이런 함수들을 쓸 때 그런 현상이 일어남)
예를들어
console.log(1+1)
axios로 get요청하고나서 console.log(1+2) 실행해주셈
console.log(1+3)
이럴 경우에는
2, 4, 3 이 순서대로 출력이 된다.
3을 출력하는 코드가 asynchronous 처리를 지원하는 코드인데, 3을 출력할 때 오래걸리면 완료될 때 까지 잠깐 보류했다가 다른 코드를 먼저 실행시킨다는 소리이다.
심지어 ajax요청이 0.00초 걸려도 4가 먼저, 그 다음 3이 출력된다. 물리적으로 잠깐 처리가 보류되어서 그렇다! (신기하다)
리액트의 setState 함수 특징
리액트로 state 만들 땐
function App(){
let [name, setName] = useState('kim')
}
setName을 사용하시면 name이라는 state를 자유롭게 변경가능
setName('park') 이런 식으로 하면 변경!
근데 문제는 변경함수들은 전부 비동기적으로 처리된다.
이럴 경우 예상 치 못한 문제가 발생할 수 있다.
function App(){
let [count, setCount] = useState(0);
let [age, setAge] = useState(20);
return (
<div>
<div>안녕하십니까 전 {age}</div>
<button>누르면한살먹기</button>
</div>
)
}
버튼을 누를 때마다
(1) count라는 state를 +1 (버튼누른 횟수 기록용)
(2) age라는 state도 +1
(3) count 가 3 이상이면 더 이상 age라는 state를 1 더하지 말도록
버튼 3번 이상 누르면 (count가 3 이상이면) 나이를 그만더하라는 기능으로 22살에서 멈춰야한다.
그러면
<button onClick={()=>{
setCount(count+1);
if ( count < 3 ) {
setAge(age+1);
}
}}>누르면한살먹기</button>
이런식으로 코드를 짜면 되는데 23까지 증가한다. 분명 22까지 증가하도록 코드를 짰는데 왜 이런 결과가 나올까?
이유는 async라는 특징 때문이다.
state 변경함수는 async(비동기방식) 하게 처리되는 함수기 때문에 완료되기까지 시간이 오래걸리면 제쳐두고 다음 코드를 실행 시킨다.
① 버튼을 세번째 누르면 setCount(count+1); 이걸 실행해서 count를 3을 만들어준다.
② 근데 count를 3으로 만드는건 오래걸리니까 제껴두고 if ( count > 3 ) {} 이걸 실행한다.
③ 이 때 count는 아직 2라서 if문 안의 setAge(age+1)이 잘 동작하고 있는것
결론 : setCount()가 async 함수라서.
async함수는 오래걸리면 제껴두고 다음 줄 코드부터 실행
해결 방법 ? sync스럽게, 순차적으로 실행하고 싶을 때 해결책은 useEffect이다.
import React, { useState, useEffect } from 'react';
import './App.css';
function App() {
let [count, setCount] = useState(0);
let [age, setAge] = useState(20);
useEffect(()=>{
if(count !=0 && count<3){
//처음 페이지 로드시 useEffect 실행을 막는 코드로
//count가 0이 아닐 때만 실행하라고 조건을 추가
setAge(age+1)
}
},[count])
//뒤에다가 [] 대괄호안에 state를 집어넣으면 state가 변경되면 이 코드 실행해주세요~ 라는 뜻
return (
<div>
<div>안녕하십니까 전 {age}</div>
<button onClick={()=>{
setCount(count+1);
}
}>누르면한살먹기</button>
</div>
)
}
export default App;
'Front-end > React' 카테고리의 다른 글
Props vs State vs Redux (0) | 2022.01.30 |
---|---|
[React] 코딩애플 blog-part3-8 (성능 잡기 - lazy loading / React devtools / memo) (0) | 2022.01.11 |
[React] 코딩애플 blog-part3-6 (리액트에서 자주쓰는 if문 작성패턴 5개) (0) | 2022.01.09 |
[React] 코딩애플 blog-part3-4 (장바구니 기능 완성) (0) | 2022.01.09 |
[React] 코딩애플 blog-part3-4 (reducer/dispatch로 데이터 수정 및 전송) (0) | 2022.01.05 |