react) filter를 이용하여 검색 기능 만들기

이명진·2021년 4월 10일
1
post-custom-banner

fetch,map(),props등을 복습하는 과제 겸 filter를 이용해서 검색 기능을 구현하는 과제를 받게 되었다.

filter를 이용해서 검색 기능을 하게 되면 아래와 같이 된다.

과제에서 친절하게 주석으로 힌트가 주어져서 쉽게 도전할수 있었다.

몬스터 카드들은 데이터를 fetch로 받아 map을 통해 데이터를 구현한 것인데
오늘은 filter 기능에 대한 포스팅이니 생략하도록 하겠다.

부모 컴포넌트

class Monsters extends Component {
  state = {
    monsters: [],
    userInput: '',
  };
  handleChange = (e) => {
    this.setState({
      userInput: e.target.value,
    });
  };

  render() {
    const { monsters, userInput } = this.state;
    const MATCHVALUE = monsters.filter((monsters) =>
      monsters.name.toLowerCase().includes(userInput)
    );
    return (
      <div className="Monsters">
        <h1>컴포넌트 재사용 연습!</h1>
        {/* <SearchBox handleChange=정의한메소드 /> */}
        <SearchBox handleChange={this.handleChange} />
        <CardList monsters={this.state.monsters} matchvalue={MATCHVALUE} />
      </div>
    );
  }
}

상위 컴포넌트에서 이미 데이터를 받아 state의 monsters배열에 넣어주었다.
간략하게 이 기능 구현을 요약해 보자면
monster 객체의 name 값을 소문자로 변경하여 userInput과 비교하는 filter 를 만든 다음에 filter 메소드가 반환하는 값을 변수에 저장 후 return 문 안에 CardList에 props로 전달하고 filter된 값들을 다시 map으로 돌려주는 것이다.

자세한 해답

만약 이 문제를 풀면서 힌트를 얻고 싶었고 스스로 풀기 원한다면 이 아래 글은 읽을 필요가 없다.

처음에 어렵게 생각해서 나도 벨로그를 보면서 문제를 해결하려고 했는데
다른 벨로그에서는 마지막 단계 에서 애매모호 하게 알려주어서 혼자서 사투하다 스스로 문제를 해결하게 되었다.

부모 컴포넌트에서 사용자가 찾고자 하는 값을 받기 위해 this.state에서 userinput이라는 키를 만들어 주었다.

class Monsters extends Component {
  state = {
    monsters: [],
    userInput: '',
  };

이후 userinput에 값을 저장하기 위한함수를 제작해준다.

handleChange = (e) => {
    this.setState({
      userInput: e.target.value,
    });
  };

handleChange 함수를 onchange이벤트가 실행될 경우로 하여 값을 받아왔고 그 값을 userinput에 저장해준다.
이 handleChange 함수를 searchBox에 전달하여 input에 입력될때 값을 가지고 온다.

 render() {
    const { monsters, userInput } = this.state;
    const MATCHVALUE = monsters.filter((monsters) =>
      monsters.name.toLowerCase().includes(userInput)
    );
    

이 부분에서는 함수를 만들거나 변수에 할당하는 방법 두가지 방법을 보았는데
나는 변수에 할당하는 방법을 사용하였다.
MATCHVALUE 상수를 만들어 monsters 데이터를 필터링해준다.
필터링에 화살표 함수를 사용하였으며 몬스터의 이름을
toLowerCase()를 사용해서 소문자로 변경시켜주고 userInput값과 비교한다.
이 변수를 CardList에 전달해준다.

하위 컴포넌트

SearchBox는 onchange값에 전달해주면 되기 때문에 생략하도록 한다.
CardList에 MATCHVALUE 상수를 전달해 주긴했는데 어떻게 사용해야 할까 ?
힌트는 render함수에 그대로 적용하라고 나와 있었다.
그래서 return에서 render함수를 다시 사용해야 할지 . 어디에 넣어야 할지 고민고민 하던 중 filter 를 돌리면 배열로 결과가 나온다는 힌트를 얻을수 있었다.
필터로 준 조건에 맞는 내용들이 배열로 담긴다면 어떻게 사용해야 할까 ?

간단하다. 기존의 map을 돌린 배열 의 자리를 변경해주면된다

아래는 하위 컴포넌트 코드 이다.

class CardList extends Component {
  render() {
    const { monsters, matchvalue } = this.props;

    return (
      <div className="card-list">
        {matchvalue.map((matchvalue) => (
          <Card
            id={matchvalue.id}
            name={matchvalue.name}
            email={matchvalue.email}
          />
        ))}
      </div>
    );
  }
}

기존에는 monsters.map이었는데 matchvalue 값을 map으로 돌리도록 변경해 주었다.

결과는 맨위 에서 확인할수 있다.

과제를 통해서 toLowerCase()와 filter 에 대해서 알수 있었다.
오늘도 조금 발전한것 같다.

filter로 검색 구현하기 완료 !

profile
프론트엔드 개발자 초보에서 고수까지!
post-custom-banner

0개의 댓글