본문 바로가기

개발/React

React - 4) State

React Docs 공식 문서를 읽고 이해한 내용을 정리한 포스트

1) 명령형 vs 선언형

- 명령형은 상태와 제어흐름이 존재하며 상태를 필요에 따라 생성하고 정의하고 변경하는 언어를 의미하며, 대표적으로 C/C++/Python/JAVA 등이 있다.
- 하지만 선언형 언어는 상태와 제어 흐름이 존재하지 않으며 약속된 정의만 사용해서 작성하는 언어를 의미한다고 한다. 대표적으로는 HTML/CSS/XML 등이 있다.

- 명령형은 어떻게 할 것인지 설명하고(how), 선언형은 무엇을 할 것인지 정의한다(what). 명령형 언어를 통해서도 비선언형 부분을 캡슐화 하여 선언형이 가능하다고 한다.(...)

 

 

2) Updates

- mutation : object 자체 값을 변경하는 것.

- 기본적으로 object들은 mutable이지만 immutable인 것 처럼 취급하여, 변경하는 것 보다 대체해서 활용하는 것이 좋다.

// Object 자체 값을 변경 (Not Desired)
onPointerMove={e => {
  position.x = e.clientX;
  position.y = e.clientY;
}}

// 새로운 Object를 만들어 pass (Desired)
onPointerMove={e => {
  setPosition({
    x: e.clientX,
    y: e.clientY
  });
}}

이때, {...obj, something: 'newValue'}와 같은 spread 구문을 통해 shallow copy를 얻을 수 있다.

 

- 마찬가지로 array역시 mutable이지만 immutable처럼 취급해야 한다 : filter나 map등을 이용하여 새로운 array를 만들어 이를 pass해주는 것이 바람직하다.

// map을 사용하여 array update를 수행하는 모습
      <ul>
        {artists.map(artist => (
          <li key={artist.id}>{artist.name}</li>
        ))}
      </ul>

update와 마찬가지로 update, insert, transform등을 map과 filter를 사용하여 수행할 수 있다.

 

 

 

3) Usage

- Hook으로 선언하고 setter로 사용하는 변수.

- 컴포넌트에서 동적인 값을 상태(state)라고 부르며, 동적인 데이터를 다룰 때 사용된다. 즉 component에서 변경 가능한 데이터를 관리할 때 사용한다. props는 부모 컴포넌트가 설정하고, 컴포넌트 자신은 props를 바꾸지 못하는 특성이 있는 것과는 비교된다.

- prop등의 값은 변경하지 않는것이 바람직하지만, prop도 변경되긴 한다고 한다(...)

- 일반 변수는 변수값이 변해도 새롭게 렌더링 되지 않지만, state는 값이 변경될 경우 새로 rendering을 수행한다. 따라서 여러 번 state가 변경되는 경우, rendering을 자주 해주어야 해서 overhead가 커진다. 그러므로 state 변경은 가능한 최소한으로 수행하는 것이 좋다.

//Not Desired
const [x, setX] = useState(0);
const [y, setY] = useState(0);

//Desired
const [position, setPosition] = useState({ x: 0, y: 0 });

 

4) Prop drilling

: 리액트의 컴포넌트 트리에서 데이터를 전달하기 위해서 필요한 과정을 의미.

- props를 오로지 하위 Component로 전달하는 용도로만 쓰이는 Component들을 거쳐 React Component 트리의 한 부분에서 다른 부분으로 데이터를 전달한다.

- component composition(합성) : 컴포넌트에서 다른 컴포넌트를 담는 것.

 

여러 컴포넌트를 거치게 된다면, 중간 컴포넌트들은 불필요하게 prop을 전달받으며 가독성이 떨어지고, 유지보수에 어려움을 겪는다. 이를 해결하기 위해서는 전역 상태관리 라이브러리를 사용하는데, 대표적으로 context api를 사용한다.

 

- Context : React에서 데이터는 위에서 아래로 (부모 > 자식) props를 통해 전달되지만, 여러 컴포넌트들에 전해줘야 하는 props의 경우 사용. global로 데이터를 공유한다.

const ThemeContext = React.createContext('light');

class App extends React.Component {
  render() {
    // Provider를 이용해 하위 트리에 테마 값을 보내준다.
    // 아무리 깊숙히 있어도, 모든 컴포넌트가 이 값을 읽을 수 있다.
    return (
      <ThemeContext.Provider value="dark">
        <Toolbar />
      </ThemeContext.Provider>
    );
  }
}

// 중간 컴포넌트가 일일이 테마를 넘겨줄 필요가 없다.
function Toolbar() {
  return (
    <div>
      <ThemedButton />
    </div>
  );
}

class ThemedButton extends React.Component {
  static contextType = ThemeContext;
  render() {
    return <Button theme={this.context} />;
  }
}

context를 사용하면 컴포넌트를 재사용하기가 어려워지므로, 필요할때만 사용해야 한다.

'개발 > React' 카테고리의 다른 글

React - 6) To-Do List ~ Local Storage  (0) 2022.07.01
React - 5) To-Do List  (0) 2022.06.30
React - 3) Interactivity  (0) 2022.06.24
React - 2) React Design  (0) 2022.06.23
React - 1) React 환경설정  (0) 2022.06.23