[React] 배열

유희옥·2023년 2월 15일
0

React

목록 보기
7/7
post-thumbnail

배열

1. 배열 렌더링하기

<아래의 배열 랜더링하기>

const users = [
  {
    id: 1,
    username: 'velopert',
    email: 'public.velopert@gmail.com'
  },
  {
    id: 2,
    username: 'tester',
    email: 'tester@example.com'
  },
  {
    id: 3,
    username: 'liz',
    email: 'liz@example.com'
  }
];

<랜더링 1>

import React from 'react';

function UserList() {
  const users = [
    {
      id: 1,
      username: 'velopert',
      email: 'public.velopert@gmail.com'
    },
    {
      id: 2,
      username: 'tester',
      email: 'tester@example.com'
    },
    {
      id: 3,
      username: 'liz',
      email: 'liz@example.com'
    }
  ];
  return (
    <div>
      <div>
        <b>{users[0].username}</b> <span>({users[0].email})</span>
      </div>
      <div>
        <b>{users[1].username}</b> <span>({users[1].email})</span>
      </div>
      <div>
        <b>{users[2].username}</b> <span>({users[1].email})</span>
      </div>
    </div>
  );
}

export default UserList;

<랜더링 1-1 컴포넌트 재활용>

import React from 'react';

function User({ user }) {
  return (
    <div>
      <b>{user.username}</b> <span>({user.email})</span>
    </div>
  );
}

function UserList() {
  const users = [
    {
      id: 1,
      username: 'velopert',
      email: 'public.velopert@gmail.com'
    },
    {
      id: 2,
      username: 'tester',
      email: 'tester@example.com'
    },
    {
      id: 3,
      username: 'liz',
      email: 'liz@example.com'
    }
  ];

  return (
    <div>
      <User user={users[0]} />
      <User user={users[1]} />
      <User user={users[2]} />
    </div>
  );
}

export default UserList;

배열의 인덱스를 하나하나 조회해가면서 랜더링, 이러한 랜더링은 동적인 배열을 랜더링 하지 못한다.


동적인 배열을 랜더링하기 위해서는 자바스크립트 배열의 내장함수 map()을 사용한다.


1-1. Map을 이용한 렌더링

  • map() 함수는 배열안에 있는 각 원소를 변환하여 새로운 배열을 만들어줌
  • map() 함수를 사용하여 일반 데이터 배열 -> 리액트 엘리먼트로 이루어진 배열로 변환

import React from 'react';

function User({ user }) {
  return (
    <div>
      <b>{user.username}</b> <span>({user.email})</span>
    </div>
  );
}

function UserList() {
  const users = [
    {
      id: 1,
      username: 'velopert',
      email: 'public.velopert@gmail.com'
    },
    {
      id: 2,
      username: 'tester',
      email: 'tester@example.com'
    },
    {
      id: 3,
      username: 'liz',
      email: 'liz@example.com'
    }
  ];

  return (
    <div>
      {users.map(user => (
        <User user={user} />
      ))}
    </div>
  );
}

export default UserList;

하지만 console 창을 살펴보면 이러한 에러가 찍혀있다

리액트에서 배열을 랜더링할때에는 key라는 props를 설정해야한다.

-> 배열이 업데이트 될 때 효율적으로 렌더링 할 수 있기 때문이다.
수정되지 않은 기존의 값은 그대로 두고 원하는 곳에 내용을 삽입하거나 삭제한다.
Map에 key값이 없다면 중간의 값이 바뀌었을 때 그 하위 값들이 전부 변하게 된다.


<배열 안에 있는 고유값 id를 key값으로 설정함>

  return (
    <div>
      {users.map(user =>(
        <User user = {user} key={user.id}/>
      ))}
    </div>
  );

<배열 안에 고유 값이 없다면 map() 함수를 사용할때 설정하는 콜백함수의 두번째 파라미터 index를 key값으로 사용한다>

  return (
    <div>
      {users.map((user, index) =>(
        <User user = {user} key={index} />
      ))}
    </div>
  );


2. 배열 추가하기

배열에 변화를 줄때에는 객체와 마찬가지로 불변성을 지켜주어야한다. 그렇기 때문에 배열의 push, splice, sort 등의 함수를 사용하면 안된다. 만약에 사용하게 된다면 기존의 배열을 한번 복사하고 나서 사용해야한다.


2-1. spread 연산자 이용

 const nextId = useRef(4);
  const onCreate = () => {
    const user = {
      id: nextId.current,
      username,
      email
    };
    setUsers([...users, user]);

    setInputs({
      username: '',
      email: ''
    });
    nextId.current += 1;
  };

<App.js> 전체 코드

import React, { useRef, useState } from 'react';
import UserList from './UserList';
import CreateUser from './CreateUser';

function App() {
  const [inputs, setInputs] = useState({
    username: '',
    email: ''
  });
  const { username, email } = inputs;
  const onChange = e => {
    const { name, value } = e.target;
    setInputs({
      ...inputs,
     [name]: value
    });
  };
  const [users, setUsers] = useState([
    {
      id: 1,
      username: 'velopert',
      email: 'public.velopert@gmail.com'
    },
    {
      id: 2,
      username: 'tester',
      email: 'tester@example.com'
    },
    {
      id: 3,
      username: 'liz',
      email: 'liz@example.com'
    }
  ]);

  const nextId = useRef(4);
  const onCreate = () => {
    const user = {
      id: nextId.current,
      username,
      email
    };
    setUsers([...users, user]);

    setInputs({
      username: '',
      email: ''
    });
    nextId.current += 1;
  };
  return (
    <>
      <CreateUser
        username={username}
        email={email}
        onChange={onChange}
        onCreate={onCreate}
      />
      <UserList users={users} />
    </>
  );
}

export default App;

2-2. concat 함수이용

  const nextId = useRef(4);
  const onCreate = () => {
    const user = {
      id: nextId.current,
      username,
      email
    };
    setUsers(users.concat(user));

    setInputs({
      username: '',
      email: ''
    });
    nextId.current += 1;
  };

<App.js> 전체 코드

import React, { useRef, useState } from 'react';
import UserList from './UserList';
import CreateUser from './CreateUser';

function App() {
  const [inputs, setInputs] = useState({
    username: '',
    email: ''
  });
  const { username, email } = inputs;
  const onChange = e => {
    const { name, value } = e.target;
    setInputs({
      ...inputs,
     [name]: value
    });
  };
  const [users, setUsers] = useState([
    {
      id: 1,
      username: 'velopert',
      email: 'public.velopert@gmail.com'
    },
    {
      id: 2,
      username: 'tester',
      email: 'tester@example.com'
    },
    {
      id: 3,
      username: 'liz',
      email: 'liz@example.com'
    }
  ]);

  const nextId = useRef(4);
  const onCreate = () => {
    const user = {
      id: nextId.current,
      username,
      email
    };
    setUsers(users.concat(user));

    setInputs({
      username: '',
      email: ''
    });
    nextId.current += 1;
  };
  return (
    <>
      <CreateUser
        username={username}
        email={email}
        onChange={onChange}
        onCreate={onCreate}
      />
      <UserList users={users} />
    </>
  );
}

export default App;

부모컴포넌트에서 state값(input 등등)과 함수를 작성하고 자식 컴포넌트에게 전달하는 구조를 기억하기


3. 배열 삭제하기

불변성을 지키면서 특정원소를 배열에서 제거하기 위해 filter 배열 내장함수 사용한다

  • filter를 사용하여 false 인 값만 담는다
  • 태그에서 변수를 전달하고 싶을땐 아래와 같이 작성한다
    const onRemove = id => {
        // user.id 가 파라미터로 일치하지 않는 원소만 추출해서 새로운 배열을 만듬
        // = user.id 가 id 인 것을 제거함
        setUsers(users.filter(user => user.id !== id));
      };

<br>

<App.js> 전체코드
>```react
import React, { useRef, useState } from 'react';
import UserList from './UserList';
import CreateUser from './CreateUser';
>
function App() {
  const [inputs, setInputs] = useState({
    username: '',
    email: ''
  });
  const { username, email } = inputs;
  const onChange = e => {
    const { name, value } = e.target;
    setInputs({
      ...inputs,
>      [name]: value
    });
  };
  const [users, setUsers] = useState([
    {
      id: 1,
      username: 'velopert',
      email: 'public.velopert@gmail.com'
    },
    {
      id: 2,
      username: 'tester',
      email: 'tester@example.com'
    },
    {
      id: 3,
      username: 'liz',
      email: 'liz@example.com'
    }
  ]);
>
  const nextId = useRef(4);
  const onCreate = () => {
    const user = {
      id: nextId.current,
      username,
      email
    };
    setUsers(users.concat(user));
>
    setInputs({
      username: '',
      email: ''
    });
    nextId.current += 1;
  };
>
  const onRemove = id => {
    // user.id 가 파라미터로 일치하지 않는 원소만 추출해서 새로운 배열을 만듬
    // = user.id 가 id 인 것을 제거함
    setUsers(users.filter(user => user.id !== id));
  };
  return (
    <>
      <CreateUser
        username={username}
        email={email}
        onChange={onChange}
        onCreate={onCreate}
      />
      <UserList users={users} onRemove={onRemove} />
    </>
  );
}
>
export default App;


profile
기록자

0개의 댓글