리액트에서도 DOM을 선택해야 할 상황이 생긴다. 예를 들면 네이버에서 화면이 렌더링 되자마자 특정 input
태그가 포커싱이 되어야 하는 경우이다.
useRef("초기값")
const countRef = useRef(0);
countRef.current;
countRef.current
로 초기값에 접근할 수 있다. (countRef는 객체)
설정된 ref값은 컴포넌트가 계속 렌더링되어도 unmount 전까지는 값을 유지한다.
(1) state와 ref의 차이점
state와 비슷한 역할을 한다.
state
리렌더링이 꼭 필요한 값을 다룰 때 사용ref
리렌더링을 발생시키지 않는 값을 저장할 때 사용(2) DOM 요소 접근
<input />
태그에 ref
라는 속성을 넣어 DOM 요소에 접근할 수 있다.
function App() {
// 1. useRef 만들어 주기
const idRef = useRef("");
// 2. useEffect를 사용하여 렌더링 될 때 idRef.curren에 focus() 주기
useEffect(() => {
idRef.current.focus();
}, []);
// 3. input 태그에 ref 속성으로 idRef 불러오기
return (
<>
<div>
아이디 : <input type="text" ref={idRef} />
</div>
<div>
비밀번호 : <input type="password" />
</div>
</>
);
}
export default App;
전역적으로 사용되는 데이터를 저장, 공유하여 데이터가 필요한 컴포넌트에서 바로 사용이 가능하게 한다.
GrandFather
컴포넌트에서 Child
로 props를 전달해 주기 위해 Father 컴포넌트를 거칠 수밖에 없다. 깊이가 너무 깊어지면 이 props가 어디에서 왔는지 파악하기 어려워진다. 이 prop drilling 문제를 해결하기 위해 context API를 사용한다.Context API 필수 개념
createContext
: context 생성Consumer
: context 변화 감지Provider
: 하위 컴포넌트에 context 전달
createContext(initialValue)
로 객체 생성context 폴더를 생성하고 폴더 안에 FamilyContext.js
파일을 생성한다.
createContext
로 전역 데이터를 저장할 Context를 생성한다. 이 때 Provider를 사용하지 않았을 때 적용될 초기값을 설정할 수 있는데, 초기값을 따로 지정하지 않을 경우 null을 입력한다.
import { createContext } from "react";
export const FamilyContext = createContext(null);
Provider
로 하위 컴포넌트에 전달프로퍼티로 value를 넘겨준다. (value는 객체로, key-value가 같으면 생략)
이제 더이상 Father 컴포넌트와 Child 컴포넌트에서는 props를 받아올 필요가 없다.
import React from "react";
import Father from "./Father";
import { FamilyContext } from "../context/FamilyContext";
function GrandFather() {
const houseName = "스파르타";
const pocketMoney = 10000;
return (
<FamilyContext.Provider value={{ houseName, pocketMoney }}>
<Father />
</FamilyContext.Provider>
);
}
export default GrandFather;
useContext
로 불러오기여기서 data는 Provider에서 value값으로 준 객체
import React, { useContext } from "react";
import { FamilyContext } from "../context/FamilyContext";
function Child() {
const data = useContext(FamilyContext);
return (
<div>
<br />
할아버지가 우리 집 이름은 <span>{data.houseName}</span>
라고 하셨어요.
<br />
게다가 용돈도 <span>{data.pocketMoney}</span>원 만큼이나 주셨어요
</div>
);
}
export default Child;
useContext의 렌더링 문제
Provider
에서 제공한value
가 달라지면useContext
를 사용하고 있는 모든 컴포넌트가 리렌더링되어 매우 비효율적이다. → 메모이제이션
오늘부터 알고리즘 스터디를 시작했다. Level.0 단계는 너무 빨리 풀 수 있는 문제들이 많아서 Level.1 중에 하나를 골라서 갔다. 서로 푼 방식을 공유하고, 겪은 시행착오를 공유하면서 새로운 개념들을 배울 수 있었다. 조원분 중 한명이 못풀었던 문제를 공유하면서 조원들끼리 같이 풀었고, 해당 문제에 대해 각자 다시 생각해보고 내일 다시 의견을 공유하기로 했다. 조원분들 모두 열정적인 것 같다.
Create Hooks을 배우면서 개념이 잘 정리가 되지 않는다. useState는 투두리스트 만들기 과제를 하면서 어느정도 익숙해 진 것 같은데, useEffect와 useRef가 좀 헷갈린다. React Hooks 최적화 방법에 대한 강의를 들으니 머리가 아파왔다. 이해가 잘 안되어서 두번 씩 들었는데, 아직 잘 모르겠다. 내일 다시 정리해봐야겠다 ㅠㅠ