본문 바로가기
> 메모/React

[리액트] Redux 사용 ( 데이터바인딩 / state 변경 )

by 자몽주스 2024. 6. 7.
728x90
state 데이터 바인딩
cart State 추가
import { configureStore, createSlice } from "@reduxjs/toolkit";
let user = createSlice({
  name: "user",
  initialState: "김씨",
});

let stock = createSlice({
  name: "stock",
  initialState: [10, 11, 12],
});
//cart state 추가
let cart = createSlice({
  name: "cart",
  initialState: [
    { id: 0, name: "White and Black", count: 2 },
    { id: 2, name: "Grey Yordan", count: 1 },
  ],
});

// export 에다가 등록
export default configureStore({
  reducer: {
    user: user.reducer,
    stock: stock.reducer,
    cart: cart.reducer,
  },
});
state 갖다 쓰기 - Cart.js
  let state = useSelector((state) => {
    return state;
  });
  console.log(state.cart);

array 배열하고

그 안에 object 배열 출력됨.

데이터바인딩 하기 (자의적)
	  <tr>
            <td>{state.cart[0].name}</td>
            <td>안녕</td>
            <td>안녕</td>
            <td>안녕</td>
          </tr>
          <tr>
            <td>{state.cart[1].name}</td>
            <td>안녕</td>
            <td>안녕</td>
            <td>안녕</td>
          </tr>
map 반복문 갖다 쓰기
array 자료 개수만큼 반복생성하기
- array 배열일 때 사용 가능
- return 문 사용
- html 에다가 key 속성 추가
  <tbody>
          {state.cart.map((a, i) => {
            return (
              <tr key={i}>
                <td>1</td>
                <td>{state.cart[i].name}</td>
                <td>{state.cart[i].count}</td>
                <td>안녕</td>
              </tr>
            );
          })}
        </tbody>

state.cart 는 array

   {state.cart.map((a, i) => (
            <tr key={i}>
              <td>1</td>
              <td>{state.cart[i].name}</td>
              <td>{state.cart[i].count}</td>
              <td>안녕</td>
            </tr>
          ))}

return 문이랑 중괄호랑 동시 생략 가능.

return 문이랑 중괄호랑 동시 생략 이란? >>>
  <tbody>
          {state.cart.map((a, i) => {
            return (
              <tr key={i}>
                <td>1</td>
                <td>{state.cart[i].name}</td>
                <td>{state.cart[i].count}</td>
                <td>안녕</td>
              </tr>
            );
          })}
        </tbody>
<tr>...</tr> 부분이 하나의 표현식
// 원래 코드
const sayHello = (name) => {
  return `Hello, ${name}!`;
};

// 간단하게 바꾼 코드
const sayHello = (name) => `Hello, ${name}!`;​
map 함수를 사용할 때, 화살표 함수의 return문과 중괄호를 생략할 수 있다.
= 자바스크립트의 화살표 함수 문법 때문.
const add = (a, b) => {
  return a + b;
}​

 

화살표 함수는 중괄호 없이 하나의 표현식만 있을 때 그 값을 자동으로 반환
const add = (a, b) => a + b;​
a + b 는 하나의 표현식이고, 이 표현식이 자동으로 반환
( 중괄호 없이 작성된 표현식이 자동으로 반환 )
하나의 표현식이라는 것은, 값을 반환하는 코드의 단위라는 의미
const renderRow = (item, index) => (
  <tr key={index}>
    <td>{item.name}</td>
    <td>{item.count}</td>
  </tr>
); // 단일 표현식, 중괄호와 return 생략​
화살표 함수의 본문이 단일 표현식일 경우 중괄호와 return을 생략할 수 있음
= 단일 표현식이란, 함수 본문이 값을 산출하는 하나의 코드 조각으로 구성되어 있는 경우를 의미
리턴값으로 숫자, 문자열, 연산 결과 또는 JSX 요소와 같이 하나의 값이 될 수 있는 것을 반환할 때

화살표 함수의 본문이 단일 표현식(JSX 요소)일 때는,
중괄호와 return 을 생략하고 바로 표현식을 괄호로 감쌀 수 있다

자바스크립트에서 화살표 함수의 본문이 하나의 표현식(덩어리)일 때는
중괄호와 return 을 생략 가능 

state 변경하기
- reducers

kim를  john kim으로 바꾸기

let user = createSlice({
  name: "user",
  initialState: "kim",
});

 

1. state 를 수정하는 함수 생성
- store.js 에 생성하기
- reducers 사용
- return문 사용해서 state 수정
- 파라미터 사용
let user = createSlice({
  name: "user",
  initialState: "kim",
  reducers: {
    changeName() {
      return 
    },
  },
});

changeName 으로 작명 (작명 자유)

 

return 문 사용

return 추가하고 오른쪽에

새로운 state 입력

let user = createSlice({
  name: "user",
  initialState: "kim",
  reducers: {
    changeName(state) {
      return 
    },
  },
});

state를 수정할 때,

기존 state가 필요한 경우

파라미터로 state 를 넣어주기

changeName 의 파라미터로 state 를 넣어주는 이유 >>>
changeName(state) { return },​

changeName 리듀서 함수: 
리듀서 함수는 두 가지를 인수로 받습니다
1) 현재 상태(state): 리듀서 함수가 호출될 때 현재의 상태를 나타냅니다.
2) 액션(action): 상태를 변경하기 위해 발생한 이벤트를 나타냅니다.
일반적으로 액션 객체는 type 속성과 선택적으로 payload 속성을 가집니다.

파라미터로 state 를 넣는 이유:
리듀서 함수가 상태를 변경하려면 현재 상태를 알아야 합니다.
현재 상태를 파라미터로 받아서 그 상태를 변경하는 로직을 작성할 수 있습니다
현재 상태를 참조: 함수가 호출될 때 현재의 상태를 참조합니다.
상태 변경: 상태를 직접 변경하거나 새로운 상태를 반환합니다.

파라미터 이름 지정: 
파라미터 이름은 임의로 정할 수 있습니다.
state 라는 이름은 관습적으로 많이 사용되며 가독성을 높이는 역할을 합니다.

파라미터 사용 여부: 
파라미터를 반드시 사용해야 하는 것은 아닙니다.
그러나 상태를 변경하려면 현재 상태에 접근할 필요가 있기 때문에
일반적으로 리듀서 함수에서는 파라미터를 사용합니다.
상태를 변경해야 하는 경우에는 현재 상태에 접근해야 하기 때문에 파라미터가 필요합니다

changeName 함수는 현재 상태를 파라미터로 받아서 새로운 상태를 반환합니다
  • 상태를 변경하거나 상태에 접근할 필요가 없는 리듀서 함수라면 파라미터를 생략할 수 있습니다.
  • 상태를 변경하거나 상태에 접근해야 하는 경우에는 파라미터를 사용하는 것이 필수적입니다.
  • 파라미터 이름은 임의로 정할 수 있으며, 관습적으로 state라는 이름이 자주 사용됩니다.

 

let user = createSlice({
  name: "user",
  initialState: "kim",
  reducers: {
    changeName(state) {
      return "john " + state;
    },
  },
});

return 문 오른쪽에

저런 식으로 state 를 추가해줘도

john kim 이 된다

= 기존 state 값이 kim 이기 때문에

 

이제 changeName() 쓸 때 마다 'kim' -> 'john kim' 이렇게 변함

2. 다른 곳에서 쓰기좋게 export 하기
- .actions

밖으로 빼서 export 키워드를 붙이기

 changeName(state) {
      return "john" + state;
    },

reducers 에 쓴 함수를

밖으로 빼고 싶은 경우

user.actions;

state 보관함인 user 이름을 쓰고,

.actions 이라고 붙이기

= 함수들이 저기에 object 자료형 형식으로 남음

export let { changeName } = user.actions

변수에 저장했다가 export 하면 됨

export let 이라고 하고

중괄호 안에다가 export 하고 싶은 함수명을 쓰기

3. 원할 때 import 해서 사용.
- dispatch로 감싸기

Cart.js 로 가서 import

     <tbody>
          {state.cart.map((a, i) => {
            return (
              <tr key={i}>
                <td>1</td>
                <td>{state.cart[i].name}</td>
                <td>{state.cart[i].count}</td>
                <td>
                  <button>+</button>
                </td>
              </tr>
            );
          })}
        </tbody>

버튼같은거 하나 만들고

그 버튼 누르면 state를 'kim' -> 'john kim' 이렇게 변경

= onClick 사용

1) import 부터 하기
import { changeName } from "./../store.js";
2) useDispatch 라는 함수 사용
let dispatch = useDispatch();
import { useDispatch, useSelector } from "react-redux";

변수에다가 집어넣어서 사용하고 이것도 import 필요

dispatch = store.js 한테 요청 보내주는 함수

3) dispatch 함수 갖다쓰기
<button onClick={()=>{
  dispatch(changeName())
}}>+</button>

dispatch 함수 안에다가 changeName() = state 변경해주는 함수 넣어주기

728x90