일 | 월 | 화 | 수 | 목 | 금 | 토 |
---|---|---|---|---|---|---|
1 | 2 | 3 | 4 | 5 | ||
6 | 7 | 8 | 9 | 10 | 11 | 12 |
13 | 14 | 15 | 16 | 17 | 18 | 19 |
20 | 21 | 22 | 23 | 24 | 25 | 26 |
27 | 28 | 29 | 30 | 31 |
- useMemo
- 프론트엔드
- rendering
- react code splitting
- lifting state up
- 고급타입
- state 최적화
- 배칭
- useCallback
- 타스
- 타입스크립트
- router dom
- JavaScript
- 자바스크립트
- 렌더링
- 리액트
- 렌더링 동작원리
- react router dom v6
- 자동 배칭
- TypeScript
- NextJS
- 상태 끌어올리기
- Interface
- mapped types
- Front-End
- 리액트 코드분할
- react rendering
- Next.js
- TS
- React
- Today
- Total
서녕이네 개발단지
[React] automatic batching (자동 배칭) 본문
Automatic batching
❗️automatic batching에 들어가기 앞서 batching이 무엇인지 알아야 한다.
batching
- 리액트는 기본적으로 batching을 활용한다.
batching (배칭)이란❓
-이벤트 핸들러나 hooks안에서 상태 업데이트를 묶어서 동작하도록 만들어준다. 즉, 렌더링이 한 번만 일어나게 해 준다.
배칭(batching)은 리액트가 더 나은 성능을 위해 여러 개의 state(상태) 업데이트를 하나의 re-render가 발생하도록 그룹화하는 것을 의미한다.
function App() {
const [count, setCount] = useState(0);
const [flag, setFlag] = useState(false);
function handleClick() {
setCount(c => c + 1); // 아직 리렌더링 X
setFlag(f => !f); // 아직 리렌더링 X
// React는 함수가 끝나면 리렌더링 할 것이다 (-> 이것이 배칭)
}
return (
<div>
<button onClick={handleClick}>Next</button>
<h1 style={{ color: flag ? "blue" : "black" }}>{count}</h1>
</div>
);
}
예를 들어~ 위 예시를 보면,
하나의 클릭 이벤트 안에 두 개의 state 업데이트를 가지는 경우, React는 항상 이러한 작업을 하나의 렌더링으로 일괄 처리하였다.
다음 코드를 실행할 경우, state를 두 번 변경하지만, React는 한 번의 렌더링만 수행한 것을 확인할 수 있다.
react 17에서의 batching
리액트 17에서도 batching은 존재하였지만 지원되는 범위가 리액트 18가 달랐다.
- 오직 리액트 이벤트 핸들러 내부에서만 배칭이 적용되었다 (camel case인 onClick, onMouseMove, onLoad 등등..)
- promises, setTimeout, native event handlers들 안에서는 배칭이 되지 않았다.❌
react 18에서의 batching (automatic batching)
새롭게 버전업이 된 react 18에서는 automatic batching으로 인해 react 17에서 보던 배칭과는 다른 점을 볼 수 있다.
automatic batching
- automatic batching, 자동 배칭이란❓
말 그대로 모든 업데이트가 자동으로 배칭 됨을 의미.
리액트 이벤트 핸들러 내부뿐만 아니라 promises, setTimeout, native event handlers들 안에서도 배칭이 적용된다.
하지만❗️ 여기에는 조건이 존재한다.
- createRoot를 사용했을 때만 automatic batching이 적용된다. ⭕️
- 이전 legacy인 render를 사용하게 되면 리액트 18 버전이어도 automatic batching이 적용되지 않는다.❌
const root = ReactDOM.createRoot(document. getElementByld('root'));
root.render(
<React.StrictMode>
<App />
</React.StrictMode>
);
👉🏻 createRoot라서 자동 배칭 적용 가능!!
ReactDOM.render(
<React. StrictMode>
<App />
</React.StrictMode>,
document. getElementByld("root")
);
👉🏻 이전 legacy인 render를 사용하여 자동 배칭 적용 불가!!
batching을 원하지 않을 경우엔? (flushSync)
flushSync
배칭을 강제적으로 하지 않게 만드는 것은 흔하게 발생해서는 안 되는 일이고 일반적인 과정은 아닐 것이다.
하지만 일부 코드는 상태 변경 직후에 DOM에서 무언가를 읽어야 할 수도 있을 것이다.
이러한 경우에는 ReactDOM.flushSync()를 사용하여 배칭을 선택적으로 하지 않을 수도 있다.
import { flushSync } from "react-dom";
function handleClick() {
flushSync(() => {
setCounter((a) => a + 1);
});
// 이 과정이 끝났을 때 React는 DOM을 업데이트한 상태
flushSync(() => {
setNumber((b) => !b);
});
// 이 과정이 끝났을 때 React는 DOM을 업데이트한 상태
}
💡 flushSync안의 setState 개수가 아닌 flushSync가 하나의 렌더링으로 처리된다.
참고
https://velog.io/@dbwjd5864/React-18-automatic-batching에-대해-알아보자
'프론트엔드 > React' 카테고리의 다른 글
[React] state 최적화를 위한 방법? (hooks 최적화) (0) | 2023.06.19 |
---|---|
[React] React-Router-Dom V6의 동작원리 (0) | 2023.06.16 |
[React] Code Splitting (코드 분할) (0) | 2023.06.11 |
[React] Lazy Loading (지연 로딩), Suspense (서스펜스) (0) | 2023.06.11 |
[React] 렌더링 최적화 (0) | 2023.06.11 |