8가지 반응 성능 팁: 당신의 응용 프로그램을 빠르게 연소시킵니다!

16591 단어 reactjavascript
최적화는 모든 개발자의 가장 중요한 부분 중 하나이며 특히 웹 응용 프로그램을 구축할 때 더욱 그렇다.React는 가상 DOM을 사용하여 UI를 최대한 효율적으로 업데이트합니다.
React가 어떻게 작동하는지
각 React 응용 프로그램은 트리 구조의 여러 구성 요소로 구성됩니다.구성 요소는 받은 도구에 따라 UI를 렌더링하는 함수입니다.데이터가 변경될 때마다 현재 사용자 인터페이스와 새 사용자 인터페이스 간의 차이를 분석한 다음 브라우저의 실제 사용자 인터페이스에만 사용자 인터페이스 변화를 적용해야 한다.중복 비교와 렌더링 구성 요소는 성능 문제의 주요 원인 중 하나일 수 있습니다.
우리는 수신된 데이터(상태 또는 도구)의 변경에 영향을 받는 구성 요소만 다시 보여 주기를 원합니다.본고에서 응용 프로그램의 전체 성능을 향상시키기 위해 8가지 다른 기술을 보여 드리겠습니다.우리 일을 시작합시다!
  • 인덱스를 키로 사용하지 않음
  • UseEffect() 및 UseCallback()
  • 반응.비망록
  • 반응.세그먼트
  • 지연 로드
  • 점진적 이미지
  • CSS 애니메이션이 아닌 JS 애니메이션
  • 프로덕션 구축
  • 0. 설정


    먼저 axios를 사용하여 API에서 데이터를 가져오고 목록을 UI에 표시하는 기본적인 React 기능 구성 요소를 만듭니다.우리 주에서는 불러오기, 오류, 데이터 단원의 입력을 추적할 것이다.useEffect와useCallback을 결합하면, 렌더링할 때마다 API를 다시 호출하지 않도록 할 수 있습니다.
    API에 대해 나는 무작위로 재미있는 공공 API, 칵테일 데이터베이스 API를 선택할 것이다.Here 무료 공공 API 목록을 찾을 수 있습니다.
    새 React 응용 프로그램 npx create-react-app perf-test 을 만들고 위의 코드를 불러옵니다.
    성과를 평가하다.
    Chrome 성능 탭을 사용하여 React 애플리케이션의 성능을 평가합니다React suggests.모든 Chrome 확장, 특히 React DevTools가 비활성화되어 있는지 확인합니다.왜냐하면 그것들은 결과를 현저하게 왜곡시킬 수 있기 때문이다.또한 더 많은 데이터와 더 느린 시스템을 복제하기 위해 CPU 속도를 6배로 제한합니다.

    1. 인덱스를 키로 사용하지 않기


    위에서 만든 예시에서 25가지 칵테일 레시피를 포함하는 목록을 얻었습니다. 사용자는 자신의 레시피를 목록에 추가할 수 있습니다.
    사용자가 새 칵테일을 추가할 때, ddCocktail () 함수는 칵테일의 상태 연결을 업데이트합니다.useRef () 를 사용하면 입력 필드를 인용하여 빈 필드가 아니라는 것을 확인할 수 있습니다.
    이 예에서 문제는 우리가 새로운 레시피를 추가할 때마다 구성 요소가 완전히 다시 나타난다는 것이다.Chrome Devtools에서 깜빡임 그리기를 활성화하면 업데이트된 DOM 노드를 볼 수 있습니다.

    렌더링 시간: 336ms
    우리 그룹의 칵테일 하나하나가 오른쪽으로 색인을 밀어붙이기 때문이다.색인 대신 고유 ID를 사용하는 것이 크게 향상되었습니다.npm 패키지 uid를 사용하여 고유한 ID를 생성할 수 있습니다.
    ...
    const updatedCocktails = [
            {
              idDrink: uuidv4(),
              strDrink: currentName,
              strInstructions: currentDescription
            }
          ].concat(cocktails);
    ...
    cocktails.map((cocktail, index) => {
              const { idDrink, strDrink, strInstructions } = cocktail;
              return (
                <div key={idDrink}>
                  <strong>{strDrink}</strong> - {strInstructions}
                </div>
              );
            })
    ...
    
    렌더링 시간: 233ms
    경탄할 만한!계속합시다.

    2. useEffect() 및 useCallback()


    우리는 useffect () 갈고리를 사용하여 구성 요소를 설치한 후 바로 칵테일을 꺼내고 있습니다.의존항이 변할 때만 다시 실행됩니다. (이 경우 getCocktails 함수) useCallback () 을 사용하면 구성 요소가 다시 나타날 때마다 API 데이터를 가져오지 않습니다.
    우리의 예시에서, 이것은 큰 차이가 발생하지 않지만, 여러 개의 하위 구성 요소를 포함하는 대형 구성 요소가 있을 때, getCocktails가 부모 구성 요소의 상태나 도구를 바꾸면, 이 구성 요소를 완전히 다시 렌더링하지 않으면 큰 차이가 발생할 수 있습니다.
    function App() {
    
    const getCocktails = useCallback((query) => {
        axios
          .get(`https://www.thecocktaildb.com/api/json/v1/1/search.php?f=${query}`)
          .then((response) => {
            setCocktails(response.data.drinks);
            setIsLoading(false);
          })
          .catch((error) => {
            setErrors(error);
          });
      }, []);
    
      useEffect(() => {
        getCocktails("a");
      }, [getCocktails]);
    
    }
    
    위 코드에서 getCocktails가 변경될 때마다 이 효과는 getCocktails의 최신 버전을 확보하기 위해 다시 실행됩니다.getCocktails 함수는 매번 App 재구성할 때마다 다시 만들어지고 useCallback 함수를 사용하지 않으며 App에서 상태나 도구를 변경할 때 무한 순환을 호출합니다.useCallback 함수 성명과 정의 함수를 둘러싼 의존항을 통해 이러한 상황을 방지할 수 있습니다. 함수의 의존항이 변할 때만 함수를 다시 만들 수 있습니다.따라서 더 이상 모든 렌더링 주기에 이 함수를 재구성하지 않습니다.

    3. 메모리 반응 구성 요소


    반응을 보이다.Memo는 결과를 기억하여 다른 구성 요소를 감싸는 고급 구성 요소 (HOC) 이다. 이것은 React가 렌더링 구성 요소를 건너뛰고 마지막 렌더링 결과를 다시 사용한다는 것을 의미한다.이것은 너의 응용 프로그램의 성능을 향상시킬 수 있다.
    우리는 칵테일div를 자신의 무상태 기능 구성 요소에 저장하고 React로 포장할 수 있다.비망록().
    // index.js
    ...
    cocktails.map(({ idDrink, ...otherProps }) => (<Cocktail key={idDrink} {...otherProps} />))
    ...
    
    // Cocktail.js
    import React from "react";
    
    const Cocktail = ({ strDrink, strInstructions }) => {
      return (
        <div>
          <strong>{strDrink}</strong> - {strInstructions}
        </div>
      );
    };
    
    export default React.memo(Cocktail);
    
    렌더링 시간: 192ms

    4. 반응한다.조각조각


    React에서는 한 어셈블리에 여러 어셈블리가 있는 것이 일반적입니다.너는 항상 너의 아이를 하나의 주요 부분으로 나누어야 한다.세그먼트를 사용하면 주 패키지 구성 요소에 더 많은 DOM 노드를 추가하는 것을 피할 수 있습니다.<Fragment> 태그를 사용하고 React에서 가져올 수도 있고 빈 태그<></>를 사용할 수도 있습니다.
    예:
    return (
        <>
          <h2>Cocktails</h2>
          {!isLoading ? (
            cocktails.map(({ idDrink, ...otherProps }) => (
              <Cocktail key={idDrink} {...otherProps} />
            ))
          ) : (
            <p>Loading...</p>
          )}
        </>
      );
    
    우리의 예시에서, 차이는 매우 작지만, 만약 수십만 개의div를 사용하는 구성 요소가 있다면, 그것은 성능에 있어서 매우 큰 차이를 일으킬 수 있다.

    5. 로드 지연


    React의 또 다른 원생 방법은 React이다.현재 구성 요소가 렌더링되면 요청한 구성 요소를 불러옵니다.
    예를 들면 다음과 같습니다.
    // Normal
    import Home from '../screens/Home';
    // Lazy
    const Home = lazy(() => import("../screens/Home"));
    
    사용자가 구성 요소를 불러올 때 예비 항목을 볼 수 있도록 <Suspense> 구성 요소에서 타성 구성 요소를 호출해야 합니다.
    <Suspense fallback={<Fragment>Loading...</Fragment>}>
       <Switch>
          <Route exact path="/" component={Home} />
       </Switch>
    </Suspense>
    

    6. 점진적 이미지 로드


    매스컴에 있는 사진 봤어?com이 불러올 때 흐려졌나요?점진적인 이미지 로드를 사용하고 있습니다. 이것은 기본적으로 고해상도 이미지를 로드할 때 질이 낮은 버전 이미지를 표시할 수 있음을 의미합니다.
    react-progressive-image 패키지는 응용 프로그램에 통합하는 좋은 방법이다.
    ...
    import ProgressiveImage from "react-progressive-graceful-image";
    import ProfileImgLarge from "../assets/img/profile-large.jpg";
    import ProfileImgPlaceholder from "../assets/img/profile-placeholder.jpg";
    ...
    <ProgressiveImage
       src={ProfileImgLarge}
       placeholder={ProfileImgPlaceholder}
    >
       {(src) => (
          <ProfileImage src={src} alt="Profile of Sander de Bruijn" />
       )}
    </ProgressiveImage>
    ...
    
    이 기술을 사용하면 <10kb 이미지를 자리 차지 문자로 사용자에게 직접 표시할 수 있습니다.

    7. CSS 애니메이션이 아닌 JS 애니메이션.


    많은 개발자들은 실제로 CSS 애니메이션이 JS 애니메이션보다 더 잘 표현된다고 생각하지만this article 복잡한 애니메이션을 사용할 때 정반대이다.이외에도 JavaScript 기반 애니메이션은 더 큰 유연성, 더 복잡한 애니메이션 워크플로우 및 풍부한 상호작용을 제공합니다.
    간단한 애니메이션의 경우 CSS가 잘 작동합니다.하지만 더 복잡한 문제에 대해서는 GSAP 라이브러리를 사용하는 것을 권장합니다.

    8.생산건설


    이것은 영향이 가장 크다.개발 과정에서 우리는 우리의 생활을 간소화하기 위해 대량의 부가 부품이 필요하다.그러나 사용자는 이런 추가 구성 요소를 필요로 하지 않는다.실행 yarn build (또는 npm build) 을 통해 웹 패키지는create react app를 사용할 때 출력 폴더를 구축합니다.
    렌더링 시간: <60ms
    그렇지!네가 이 교과서에서 약간의 것을 배울 수 있기를 바란다.반드시 나에게 더 많은 기교와 요령을 배워야 한다.

    좋은 웹페이지 즐겨찾기