효율적으로 사용자 인터페이스를 만들기 위한 자바스크립트 라이브러리이다. 컴포넌트 기반 개발이 가능하고, 단방향 데이터 흐름을 가지며, 가상 돔을 이용한 효율적인 업데이트가 가능하다는 특징이 있다. 또한 Client Side Rendering을 통한 Single Page Application 개발이 가능하다.개발을 위한 기능을 제공하는 도구이고, 프레임워크는 개발을 위한 구조를 제공하는 도구이다.컴포넌트 기반으로 재사용성이 뛰어나고, 단방향 데이터 흐름을 가져 데이터를 추적하여 유지보수하는 것이 용이하며, 가상 돔을 이용한 효율적인 업데이트가 가능하기 때문이다. 또한 Next.js, React Native와 같은 리액트 기반 기술의 러닝 커브를 줄일 수 있다고 생각했다.제이쿼리
- 리액트처럼 자바스크립트의 사용성을 개선하는 라이브러리이다. 여러 브라우저에서 호환성이 뛰어나다는 장점이 있지만,
가상 돔을 사용하는 리액트보다 낮은 성능을 보여줬고, 이와 동시에크롬의 점유율이 높아짐에 따라서 인기가 낮아지고 있다.
리액트에서 사용하는 자바스크립트 확장 문법으로, 자바스크립트 파일 내부에서 XML과 유사한 형태의 마크업 코드를 작성할 수 있게 해준다. 이로 인해 마크업 파일을 분리할 필요가 없어져 가독성이 개선되고 유지보수가 용이해진다.상태 변화를 추적하여 효율적인 업데이트를 수행하는 실제 DOM의 복사본이다. / 가상 돔을 통한 업데이트는 변경 사항이 적용되지 않은 가상 돔과 변경 사항이 적용된 가상 돔을 비교함으로써, 일정 시간동안 발생한 상태 변경을 일괄 적용(=Batch Update, Batching)할 수 있고 최소한의 변경만을 실제 DOM에 반영하여 리플로우와 리페인트를 최소화할 수 있다.Auto Batching
기존에는
React event handler에서만 Batch Update가 일어났다. 그러나 React 18 이후 Auto Batching 기술이 발표되면서,Promise, 타이머 함수, Native event handler에 모두 Batch Update가 적용되도록 개선되었다.
Vue의 가상 돔과의 차이점
React는 상태가 변경되면
전체 컴포넌트 트리를 다시 렌더링하고Top-down 방식으로 전체 트리를 순회하며 diff 알고리즘을 수행하여 변경된 부분을 찾는다. 반면 Vue는반응성 시스템(Reactivity System)과 가상 돔을 결합하여어떤 컴포넌트가 업데이트되어야 하는지 미리 정확히 파악할 수 있어 불필요한 비교 연산을 줄일 수 있다. / 따라서 React는React.memo, useMemo, useCallback 같은 최적화 도구를 개발자가 직접 사용해야 하지만, Vue는프레임워크 자체에서 많은 최적화를 자동으로 처리한다.
동적으로 렌더링되는 여러 요소에 고유값을 부여하기 위한 프로퍼티이다.요소마다 고유한 key를 부여하여 요소를 구별해야 한다. 그렇지 않으면 요소를 구별할 수 없어서 모든 요소를 다시 렌더링하므로 Warning이 발생한다.빈 HTML을 전달받는다. 이후 모든 페이지에 대한 자바스크립트를 다운로드받아 실행하여 'Viewable한 상태'를 완성시키고 사용자와의 상호 작용에 따라 'interactive한 상태'까지 완성한다. CSR은 (완전한 콘텐츠가 보이는)첫 로딩은 느리지만 그 이후 페이지를 이동할 때는 빠른 속도를 가지며, 검색 엔진 최적화에 불리하다는 특징이 있다. / 반면 SSR은 첫 단계에서 서버로부터 해당 페이지에 대한 'Viewable한 상태'의 완전한 HTML을 전달받는다. 이후 자바스크립트 파일을 다운로드받아 실행하여 'interactive한 상태'까지 완성한다. SSR은 첫 로딩은 빠르지만 페이지 이동 시에는 비교적 느린 속도를 가지며, 검색 엔진 최적화에 유리하다는 특징이 있다.SPA(Single Page Application)
처음에
서버에서 빈 HTML를 받아온 이후 사용자와의 상호 작용에 따라 동적으로 페이지를 렌더링하는 애플리케이션이다. /클라이언트단으로부터 필요한 데이터만을 비동기적으로 로드하기 때문에첫 로딩을 제외한 속도가 빠르고 새로고침이 발생하지 않는다는 장점이 있다.
구글이나 네이버 같은 사이트의 검색 엔진이 HTML 문서를 잘 분석하도록 하는 작업을 검색 엔진 최적화라고 한다. / CSR 방식을 사용하는 사이트들은 서버로부터 빈 HTML을 전달받기 때문에 검색 엔진에 빈 HTML이 수집되어 검색 엔진 최적화가 잘 이루어지지 않는다.Next.js와 같은 프레임워크를 이용한 SSR이나 SSG 방식을 사용하는 것이 방법이 가장 효율적이다. / CSR 방식을 사용해야 하는 경우, react-helmet, react-snap 등의 라이브러리를 통해 검색 엔진 최적화 성능을 높일 수 있다.페이지 별로 메타 데이터를 설정할 수 있도록 해주는 라이브러리이고(여전히 HTML 파일은 하나), react-snap은 페이지 별로 각각의 HTML 파일을 가지도록 해주는 라이브러리이다.재사용 가능한 독립적인 단위로, 자체적으로 상태를 가지고 이 상태에 따라 업데이트를 수행한다.class 키워드와 extends 키워드를 통해 React.Component 객체를 상속받아 만들어지는 컴포넌트이고, 함수 컴포넌트는 함수로 작성된 컴포넌트이다.constructor를 통해 상태를 관리하고 componentDidMount, componentDidUpdate, componentWillUnmount를 사용하여 생명 주기에 대한 동작을 정의한다. 반면 함수 컴포넌트는 useState Hook을 통해 상태를 관리하고 useEffect Hook을 통해 생명 주기에 대한 동작을 정의한다.간결한 코드를 작성하기 유리하다. 또한 메모리를 덜 사용한다.super(클래스 컴포넌트)
부모 클래스의 생성자(ex. React.Component 객체의 constructor)를 호출하고 실행하는 메서드.
super를 호출하기 전에는 this를 사용할 수 없다.
render(클래스 컴포넌트)
JSX를 정의하고 반환하는 메서드.
forceUpdate(클래스 컴포넌트)
강제 업데이트 메서드.
컴포넌트가 실행되어 DOM에 등록되는 시점이고, 업데이트는 컴포넌트에 변경이 생겨 DOM에 변경 사항을 적용하는 시점이고, 언마운트는 컴포넌트가 종료되어 DOM에서 제거되는 시점이다.컴포넌트에서 업데이트가 일어나는 경우
- state나 props가 변경될 때
- 부모 컴포넌트가 리렌더링될 때
- forceUpdate()로 강제 업데이트될 때 (클래스 컴포넌트에서만)
컴포넌트를 인자로 받아 새로운 컴포넌트를 반환하는 컴포넌트이다. 여러 컴포넌트에서 재사용되는 로직을 추상화할 수 있다.부모 컴포넌트에서 자식 컴포넌트로 전달하는 데이터이고, state는 컴포넌트 내부에서 관리하는 동적인 데이터이다. / 자식 컴포넌트에서 props는 Read-Only, 즉 수정할 수 없다. 변경되는 것은 state이다.단방향 데이터 플로우를 가진다는 것을 보여준다.)모든 중간 컴포넌트에서 props를 내려주는 비효율적인 작업을 의미한다. / 이러한 문제는 전역 상태 관리 라이브러리를 사용하여 해결할 수 있다.자식 컴포넌트의 상태를 부모 컴포넌트로 전달하는 방법
부모 컴포넌트에서
props를 통해 상태를 변경하는 함수를 자식 컴포넌트에 전달하고, 자식 컴포넌트에서전달받은 함수를 사용하여 부모 컴포넌트의 상태를 변경하는 방식으로 전달이 가능하다.
상태 변화를 감지하기 위해서는 상태를 변경하고자 하는 데이터의 불변성을 유지해야 한다. / 원시 타입의 값은 불변성을 가지므로 상태 변화를 잘 감지하지만, 참조 타입의 값은 불변성을 가지지 않아 상태 변화를 감지할 수 없다. 그러므로 참조 타입인 상태를 변경할 때는 스프레드 연산자 혹은 배열이나 객체의 메서드(Array.from, Array.slice, Object.assign ...)를 통해 '얕은 복사'를 하고, 이 복사본을 통해 상태를 변경해야 한다.깊은 복사
데이터 내부에 또 다른 참조 타입 데이터를 가지는 경우,JSON 메서드(JSON.stringify & JSON.parse) 혹은 lodash나 immer 등의 라이브러리를 통해 '깊은 복사'를 하고, 이 복사본을 통해 상태를 변경해야 한다.
함수 컴포넌트에서 클래스 컴포넌트의 기능을 사용하기 위한 함수이다.상태 관리를 위한 훅이다. useState는 비동기적으로 상태를 변경하고, 일정 시간(16ms)동안 변경된 상태를 일괄 적용하는 Batch Update가 수행된다.왜 state를 직접 변경하지 않고, useState를 사용해야 하는가
내부적으로 render 함수가 호출되어 렌더링이 진행되기 때문이다.
클래스 컴포넌트의 생명주기 메서드를 대체할 수 있는 훅이다.의존성 배열 없이 사용한 useEffect의 콜백 함수는 componentDidMount와 componentDidUpdate를 합친 것처럼 동작한다. 빈 의존성 배열을 가지는 useEffect의 콜백 함수는 componentDidMount처럼 동작하는 한편, return문에는 componentWillUnmount처럼 동작하는 정리 함수를 정의할 수 있다. 의존성 배열에 특정값이 들어있는 useEffect의 콜백 함수는 componentDidMount처럼 동작하는 동시에 의존성 배열에 지정된 값이 변경되었을 때는 componentDidUpdate처럼 동작한다.페인트 작업 전(= 돔 업데이트 직후)에 실행되는 훅으로, 페인트 작업 이후 실행되는 useEffect가 문제를 일으키는 경우에 대안으로 사용할 수 있다.useEffect 내부에 DOM에 영향을 주는 코드가 있을 경우 화면의 깜빡임이 발생하는데, useLayoutEffect로 변경하면 깜빡임이 발생하지 않음)복잡한 상태 관리 로직을 간결하게 작성하도록 도와주는 훅이다.(state와 action 객체를 파라미터로 받는)리듀서 함수를 switch-case문으로 정의한다. 그리고 useReducer의 파라미터로 리듀서 함수와 state의 초기값을 넣어 호출하면 state와 dispatch 함수를 반환하는데, dispatch 함수에 action 객체의 타입을 전달하여 상태를 쉽게 관리할 수 있다.Context API를 통해 상태를 전역적으로 관리할 수 있도록 도와주는 훅이다.컨텍스트 객체를 생성하고 전역에서 관리할 상태들을 정의한다. 그리고 컨텍스트 객체의 Provider를 통해 공유할 상태를 value에 명시하고 컨텍스트 객체를 공유할 컴포넌트들을 감싸면, 각 컴포넌트에서 useContext를 통해 컨텍스트 객체에 명시한 상태에 접근할 수 있다.)리액트의 라이프 사이클을 고려하여 DOM에 접근하기 위한 훅이다. DOM API를 이용하여 DOM을 직접 조작하는 것은 리액트 라이프 사이클과 관련이 없기 때문에, useRef를 사용하여 DOM을 조작해야 한다.참조 객체(ref)를 생성하고 DOM 요소의 ref 속성을 통해 DOM 요소와 참조 객체를 연결하여 참조 객체에 ‘실제 DOM 요소의 참조'를 저장한다. 이를 통해 참조 객체의 current 프로퍼티를 통해 DOM을 조작할 수 있게 된다.)렌더링에 직접 관여하지 않는다. 따라서 즉시 렌더링에 관여하지 않을 상태 관리를 위해 사용할 수 있다. (useRef를 사용한 변경 사항은 렌더링 시점에 적용!)DOM 요소의 ref 속성에는 참조 객체 대신 Callback Ref라고 부르는 콜백 함수를 전달할 수도 있다. 이 작업을 통해 해당 DOM 요소가 마운트되거나 언마운트될 때마다 실행될 동작을 정의할 수 있다. (즉 useEffect의 역할 가능!)자식 컴포넌트에서 참조 객체를 전달받을 수 있고, useImperativeHandle을 통해 자식 컴포넌트에서 부모 컴포넌트로 함수를 전달할 수 있다.useRef를 통해 참조 객체를 생성하고 자식 컴포넌트의 ref 속성을 통해 자식 컴포넌트와 참조 객체를 연결하면, 자식 컴포넌트는 forwardRef를 통해 참조 객체를 받아올 수 있다. 그리고 (forwardRef 내부에서) useImperativeHandle의 첫 번째 인자에 '부모로부터 전달된 참조 객체'를, 두 번째 인자에 '콜백 함수'를 넣고, 콜백 함수에서 '부모 컴포넌트로 전달할 자식 컴포넌트의 함수'를 반환하면 부모 컴포넌트에서도 current 속성을 통해서 자식 컴포넌트의 함수를 사용할 수 있다.)이전에 사용한 결과값을 재사용하는 훅이다.첫 번째 파라미터로 콜백 함수, 두 번째 파라미터로 의존성 배열을 저장한다. 콜백 함수에는 메모이제이션할 값을 계산하는 로직을 정의하고, 의존성 배열의 값이 변경된다면 콜백 함수를 다시 실행해서 결과값을 업데이트하고 변경되지 않는다면 기존 결과값을 재사용한다.)이전에 사용한 함수를 재사용하는 훅이다.첫 번째 파라미터로 콜백 함수, 두 번째 파라미터로 의존성 배열을 저장한다. 의존성 배열의 값이 변경된다면 새로운 함수를 생성하여 사용하고 변경되지 않는다면 기존의 함수를 재사용한다.)컴포넌트를 메모이제이션하여 props가 변경되지 않으면 리렌더링을 방지하는 고차 컴포넌트이다.React.memo로 컴포넌트를 감싸면 props의 얕은 비교를 통해 변경 여부를 판단하고, 변경되지 않았다면 이전 렌더링 결과를 재사용한다. 두 번째 인자로 비교 함수를 전달하여 커스텀 비교 로직을 정의할 수도 있다. 주로 props가 자주 변하지 않는 무거운 컴포넌트나 리스트의 아이템 컴포넌트에 사용하면 효과적이다.)const MemoizedComponent = React.memo(({ name, age }) => {
console.log('렌더링');
return (
<div>
{name}, {age}
</div>
);
});
// 커스텀 비교 함수 사용
const MemoizedComponent = React.memo(Component, (prevProps, nextProps) => {
return prevProps.id === nextProps.id; // true면 리렌더링 X
});
React.memo vs useMemo vs useCallback
- React.memo:
컴포넌트 자체를 메모이제이션- useMemo:
값(계산 결과)을 메모이제이션- useCallback:
함수를 메모이제이션
useState와 useEffect같은 Hook을 사용하여 재사용이 가능하도록 만든 함수이다. 'use'라는 이름으로 시작하고 상태 값과 해당 상태를 업데이트하는 함수를 반환하는 특징을 지닌다.코드를 여러 개의 작은 chunk로 나누어 해당 기능이 필요한 시점에 해당 chunk를 로드하는 렌더링 최적화 기술이다. / 비동기 로딩을 위해 Dynamic import와 React.lazy를 사용하고 로딩 중임을 표시하기 위해 Suspense를 함께 사용한다.Code Splitting 동작 방식
Dynamic import를 통해 코드를
여러 개의 모듈로 나눈다. 이 모듈들은 bundle.js 파일에 저장되는 것이 아니라,별도의 chunk 파일로 저장되며, 이 chunk 파일은해당 모듈이 필요한 시점에 비동기적으로 로드된다. / 한편 Dynamic import는 Promise를 반환하는데, React.lazy를 사용하면Promise를 직접 처리하지 않고 내부적으로 처리하도록 하여 비동기 로딩을 쉽게 완료할 수 있다. 또한 Suspense의 fallback 속성을 통해로딩 중일 때 표시할 컨텐츠를 지정할 수 있다.
상태 관리 라이브러리이다.하나의 중앙 집중화된 Store 객체에 상태를 저장하고 관리하는 상태 관리 라이브러리이다. / Redux Toolkit과 미들웨어(Redux Thunk, Redux Saga, Redux-observable)를 사용하여 개발 생산성을 향상(리덕스 사용성 개선, 비동기 작업의 효율적 관리)시킬 수 있고, 안정적인 DevTool을 가지고 있기 때문에 대규모 상태를 관리에 용이하다. 다만 코드의 양이 많아 보일러플레이트 코드가 발생하게 된다는 단점이 존재한다.atoms에서 상태를 저장하고 관리하는 Context API 기반 상태 관리 라이브러리이다. / 비교적 간단한 구조롤 가지기 때문에 코드의 양을 줄일 수 있지만, 대규모 상태를 관리할 때는 Rudux에 비해서는 안정성이 떨어진다.상태를 전역에서 관리하며 selector를 통해 atom에 저장된 상태를 새로운 값으로 계산할 수 있다. RecoilRoot를 통해 Recoil State를 공유할 컴포넌트들을 감싸고 각 컴포넌트에서는 useRecoilState 등의 메서드를 통해 Recoil State에 접근할 수 있다.)서버 상태를 가져와 관리하는 것에 중점을 둔 라이브러리이다. Redux, Recoil 등은 서버 상태와 동기화되지 않기 때문에 웹 스토리지 등에서 따로 관리해야하는데, React-Query, SWR 등을 사용하면 이러한 불편함을 해소할 수 있다.먼저 서버의 상태(데이터)를 가져온 후 데이터를 패칭/캐싱/동기화하는 라이브러리이다.다양한 기능을 지원한다.)React-Query의 기능
- 탭을 이동했다가 다시 돌아왔을 때, 데이터를 다시 보여준다.
- 변경된 서버 데이터를 다시 불러온다. (setInterval 대체 가능, 양방향은 아니기 때문에 Web Socket은 대체가 어려움)
먼저 캐시에서 데이터를 반환받은 후, 서버에 데이터를 가져오는 요청을 보내고 최신 데이터를 제공받는 React Hooks 라이브러리이다.간단하게 사용 가능하다.)서버의 데이터를 읽어와 fetching하는 훅으로, HTTP GET 요청 시 주로 사용한다. / (첫 번째 인자에는 고유한 queryKey, 두 번째 인자에는 Promise를 반환하는 queryFn을 넣고, 세 번째 인자에는 options을 넣을 수 있다. (querykey는 응답 데이터를 캐싱하기 위해, queryFn은 쿼리 요청을 수행하기 위해 필요하다.) 그러면 data, isLoading, isError, refetch 등 다양한 값을 반환받을 수 있는데, 이를 통해 서버 데이터와 관련된 작업을 할 수 있다.)서버의 데이터를 변경하는 훅으로, HTTP POST, PUT, PATCH, DELETE 요청 시 주로 사용한다. / (인자로 Promise를 반환하는 mutationFn을 넣어주면 mutate 함수를 반환받는데, mutationFn은 mutate의 인자로 전달된다. 그러므로 mutationFn에는 나중에 실행할 내용을 정의하고, mutate를 통해 실행된다. (mutationFn은 queryFn과 달리 곧바로 실행되지 않는다.) 한편 두 번째 인자에는 options을 넣을 수 있는데, onSuccess, onError, onSettled를 통해 추가 로직을 작성할 수도 있다.)연속으로 다음 데이터를 가져오는 훅이다. / (첫 번째 인자는 고유한 queryKey, 두 번째 인자에는 Promise를 반환하는 queryFn을 넣고, 세 번째 인자인 options에서는 getNextPageParam을 통해 다음 페이지 호출에 필요한 파라미터를 정의할 수 있다. (다른 작업도 가능!) 그러면 data, isLoading, isError, fetchNextPage, hasNextPage 등 다양한 값을 반환받을 수 있는데, 이 데이터를 통해 무한 스크롤, 페이지네이션 등을 쉽게 구현할 수 있다.)데이터를 fresh한 상태로 유지하는 시간이다. staleTime 동안에는 캐시에 저장된 데이터를 가져오고, staleTime이 경과하고 특정 조건(백그라운드 상태에서 다시 focus될 때 등)이 만족하면 새로운 데이터를 가져온다. / (기본값 0)쿼리 결과를 캐시에 저장하는 시간이다. / (기본값 5분)Suspense와 함께 사용하여 로딩 상태를 선언적으로 처리할 수 있다.QueryClient 생성 시 suspense 옵션을 true로 설정하거나 useQuery의 옵션에 suspense: true를 추가하면 된다. 그러면 데이터를 가져오는 동안 Suspense의 fallback이 표시되고, 데이터 로딩이 완료되면 컴포넌트가 렌더링된다. 이를 통해 isLoading 상태를 직접 관리할 필요가 없어지고 코드가 간결해진다. 또한 ErrorBoundary와 함께 사용하여 에러 처리도 선언적으로 관리할 수 있다.)// QueryClient 설정
const queryClient = new QueryClient({
defaultOptions: {
queries: { suspense: true },
},
});
// 컴포넌트
function UserProfile() {
const { data } = useQuery(['user'], fetchUser); // isLoading 불필요
return <div>{data.name}</div>;
}
// App
function App() {
return (
<QueryClientProvider client={queryClient}>
<Suspense fallback={<Loading />}>
<UserProfile />
</Suspense>
</QueryClientProvider>
);
}
form 요소의 값에 접근하기 위한 방식으로, 제어 컴포넌트는 useState를 사용하여 event.target.value를 상태에 저장하여 값에 접근하고, 비제어 컴포넌트는 useRef를 사용하여 DOM 요소에 접근하여 ref.current.value를 통해 값에 접근한다.높은 신뢰도의 값을 가지며 업데이트할 때마다 매번 렌더링이 발생(실시간 유효성 검사 가능)한다는 특징을 가진다. (너무 잦은 렌더링은 debounce, throttle을 통해 방지할 수 있음!)React를 사용하여 모바일 애플리케이션을 개발하기 위한 프레임워크이다. 하나의 코드로 iOS와 Android에 대한 애플리케이션을 개발할 수 있는 '크로스 플렛폼 앱' 개발 언어이고, 이는 네이티브 앱에 준하는 성능을 보여줄 수 있다.React와의 공통점
Component, JSX, props, state를 사용한다.React와의 차이점
AppRegistry를 사용한다.Component만을 사용한다.StyelSheet를 사용한다.자바스크립트의 정적 타이핑을 지원하기 위한 언어이다.디버깅과 유지 보수가 어려워진다. 타입스크립트를 사용하면 정적 타이핑이 가능해져 코드의 안정성을 높힐 수 있다.타입을 정의하기 위한 키워드이다. type은 &(앰퍼샌드)를 통해 확장이 가능하고, interface는 extends를 통해 확장이 가능하다. 동일한 이름으로 타입을 정의할 경우, type은 에러가 발생하고 interface는 자동으로 확장된다.둘 이상의 타입을 지정할 때 사용되는 타입으로, |로 표현한다.두 타입이 공통적으로 갖는 타입을 지정할 때 사용되는 타입으로, &로 표현한다.기존 타입을 변환하여 새로운 타입을 만들어주는 타입Partial<Type>Optional로 만드는 타입Readonly<Type>Read-Only로 만드는 타입Pick<Type,Keys>키를 통해 특정 속성을 고르는 타입Omit<Type,Keys>키를 통해 특정 속성을 제외하는 타입Extract<Type,Union>유니온 타입을 통해 특정 속성을 고르는 타입Exclude<Type,Union>유니온 타입을 통해 특정 속성을 제외하는 타입Record<Keys,Type>키를 통해 특정 속성들에 동일한 타입을 지정하는 타입한번의 선언으로 다양한 타입을 지정할 수 있도록 하는 타입을 파라미터화한 타입으로, 타입에 유연성을 제공하고 재사용성을 높일 수 있다.타입 파라미터(<T>)로 선언하고, 함수 호출 시 명시적으로 타입을 지정한다. 지정하지 않아도 타입 추론을 통해 자동으로 지정된다.유니온 타입이나 함수 오버로드를 대체할 수 있다.)function identity<T>(arg: T): T {
return arg;
}
// 숫자를 전달할 때
let outputNumberOne = identity(5); // 타입 추론을 통해 outputNumberOne 타입은 number
let outputNumberTwo = identity<number>(5); // 명시적으로 작성해도 된다.
// 문자열을 전달할 때
let outputStringOne = identity("Hello"); // 타입 추론을 통해 outputString 타입은 string
let outputStringTwo Two= identity<string>("Hello"); // 명시적으로 작성해도 된다.
T[] 나 Array<T> 로 해주어야 한다.)function identity<T>(arg: T[]): T[] {
console.log(arg.length);
return arg;
}
함수 오버로딩
함수를 중복 선언하여 하나의 함수에 대해 다양한 타입을 지정하는 방식이다.
정의부를 가지지 않는 함수를 여러 개 선언하여 여러 개의 타입을 지정하고, 정의부를 가지는 함수는 타입을 any로 지정하여 사용한다.function add(a: string, b: string): string; // 오버로드 함수 선언 function add(a: number, b: number): number; // 오버로드 함수 선언 function add(a: any, b: any): any { // 오버로드 함수 실행부 (any를 써준다) return a + b; } add('hello ', 'world~'); add(1, 2);
any를 쓰면 되는 것 아닌가?
any 타입을 사용하면
타입을 아예 체크하지 않기 때문에 정적 타이핑이라고 볼 수 없어코드 안정성을 보장할 수 없다.
리액트에 SSR, SSG 등의 기능을 제공하는 웹 프레임워크이다전체 페이지에 대한 DOM을 그리는 작업이 없기 때문에 초기 로딩 속도가 빠르다. (Next.js에서는 사전 렌더링까지 지원하므로 더더욱.) 또한 검색 엔진에 완전한 HTML이 수집되기 때문에 검색 엔진 최적화에 유리하다.요청이 들어왔을 때 페이지를 생성하고 반환하는 반면 SSG은 페이지를 미리 생성해놓고 요청이 들어왔을 때 반환한다. SSR은 각 요청마다 다른 정보를 보여주는 페이지나 실시간으로 업데이트되는 페이지에 적합하고 SSG는 각 요청에 항상 동일한 정보를 보여주는 페이지에 적합하다.