[lodash] debounce 사용기

해달·2022년 5월 15일
0

진행중인 사이드프로젝트에서 닉네임 변경시에 타이핑이 될 때마다
서버로 확인요청을 보내 실시간 중복검사를 해주게되었다.

대체적으로 유저들은 무언가를 타이핑할때 어떤내용을 타이핑할지 생각하고 검색하는 경우가 많기때문에

닉네임변경시에 서버로 너무 잦은요청이 가지 않도록 디바운스처리를 해주었다.


debounce ?

프로그래밍 기법 중 하나로 연이어 발생한 이벤트를 하나로 묶어서 제일 마지막에 입력 된 이벤트만 처리해주는 기법

프로젝트 내에서 lodash 라이브러리를 사용중이였고
라이브러리에있는 debounce 메서드를 이용하여 디바운스 처리를 해주었다

디바운스에 useMemo를 씌워서 최적화를 시켜주고있어 그 내용을 찾아보았다.

useMemo 는 
  - 디펜던시 배열에 변경사항이 생기면 콜백으로 넘겨준 함수를 다시 수행
  - 생기지 않으면 이전의 수행 결과를 반환

useCallback 은
  - 디펜던시 배열에 변경사항이 생기면 이번 렌더에서 새로 만든 함수를 반환
  - 생기지 않으면 이번 렌더에서 새로 만든 함수 말고 이전에 메모이제이션해뒀던 함수를 반환
  1. 컴포넌트가 처음 렌더링 될 때 debounce 인스턴스 는 새로 생성된다.

  2. useMemo 2번째 인자에 변하지않는 디펜던시 배열을 주었고

  3. 변경되지 않으니 useMemo에서 계산한 반환 값(디바운스 함수를 참조하고 있는 값) 은 변경되지 않고 함수의 값을 그대로 유지한다

  4. useMemo 내부에 있는 디바운스 함수가 리랜더링 될때마다 생성되지 않음

이전에 연산한 값 -> 디바운스함수의 주소값 하지만 이미 되어있고 변경사항이 없기때문에 그 주소값을 그대로 사용함


블로그 번역 본

React를 사용하는 경우 핸들러를 useMemo로 래핑하여 렌더링할 때마다 다시 생성되지 않도록 한다.

다시 렌더링하는 동안 함수 정의를 그대로 유지하려면 useMemo 또는 useCallback이 필요합니다.

useMemo는 종속성이 변경될 때만 다시 계산되어야 하는 메모화된 값을 저장하는 데 사용됩니다.

우리는 반환된 함수를 원하고 정확한 완전한 종속성을 갖고 변경될 때마다 업데이트하기를 원합니다. useMemo가 정확히 그 일을 합니다

💡 useMemo를 사용하면 값비싼 함수의 불필요한 계산을 피할 수 있습니다.
useMemo는 두 번째 매개변수 배열의 종속성이 변경될 때 첫 번째 매개변수(create 함수라고 함)에서 반환된 메모화된 값만 다시 계산합니다. 따라서 구성 요소가 다시 렌더링될 때마다 앱이 함수를 다시 계산하는 것을 방지할 수 있습니다.


작성한 코드

  const validateUserNickname = useMemo(
    () =>
      _.debounce((value: string) => {
        nicknameCheck(value).then(res => {
          res.message !== '사용가능한 닉네임' ? setError(errorMessage.isError) : setError(false);
        });
      }, 200),
    [errorMessage.isError]
  );

쓰로틀링 (Throttiling)

쓰로틀링 : 마지막 함수가 호출 된 후 일정 시간이 지나기 전에 다시 호출되지 않도록 하는 것

연이어 발생한 이벤트에 대해, 일정한 delay를 포함시켜 연속적으로 발생한 이벤트는 무시하는 방식을 뜻한다.

설정시간으로 1ms 를 주게되면 해당 이벤트는 1ms 최대 한번만 발생한다.

즉, delay 시간동안 호출된 함수는 무시하는 케이스이다.
주로 스크롤 이벤트에 많이 적용된다고한다.


쓰로틀링과 디바운스의 차이점

디바운스는 설정시간내에 이벤트가 계속 발생된다면 설정시간이 초기화되고
설정시간이 끝날 때까지 계속 이벤트가 발생할 경우 콜백에 반응하는 이벤트는 발생하지 않고 계속 무시된다

쓰로틀링은 마지막 함수 호출 후에 일정시간동안 호출되지 않고 무시된다
일정시간이 지나고 나서 다시한번 함수가 호출이 된다


setTimeout , _.debounce

셋타임아웃과 디바운스는 다르게 작동한다
_.debounce는 함수를 반환하고,
setTimeout은 timeOut을 취소하는 데 사용할 수 있는 ID를 반환한다

_.debounce에 의해 반환된 함수를 몇 번 호출하더라도 주어진 시간 프레임에서 한 번만 실행된다.

setTimeout은 n 밀리초 동안 대기하고 제공된 함수를 호출한다.

반면에 debounce는 함수가 마지막으로 호출된 후 n밀리초 후에만 콜백을 호출하는 함수를 반환합니다.


reference

쓰로틀링,디바운스:

useMemo debounce

setTimeout,deboucne :

0개의 댓글