Code360 powered by Coding Ninjas X Naukri.com. Code360 powered by Coding Ninjas X Naukri.com
Last Updated: Mar 27, 2024
Difficulty: Medium

What is useeffect in react?

Leveraging ChatGPT - GenAI as a Microsoft Data Expert
Speaker
Prerita Agarwal
Data Specialist @
23 Jul, 2024 @ 01:30 PM

Introduction

React's introduction of Hooks has transformed the way functional components are written and state is managed. Among these Hooks, useEffect stands out as a Swiss Army knife for handling side effects. 

What is useeffect in react?

This article will delve into the useEffect hook, providing a comprehensive understanding of its purpose, usage, and how it can be leveraged to replicate lifecycle methods in class components.

Also see, React devtools

What is the useEffect Hook?

The useEffect hook is a function that allows you to perform side effects in your functional components. Side effects are operations that need to happen outside of the scope of the function body, such as API calls, manual DOM manipulations, or subscriptions. In class components, these operations are typically placed in lifecycle methods.

Reason to Choose useEffect Hook

useEffect is chosen for its ability to encapsulate component "side effects" in a clean and organized way. It replaces several lifecycle methods with a single, unified API, making your code more concise and easier to follow. It also helps in managing side effects in a way that is consistent with React's component lifecycle, ensuring that your effects run at the correct time and in the correct order.

Importing useEffect Hook

To use useEffect, you must first import it from the React package:


import React, { useEffect } from 'react';

Structure of useEffect Hook

The useEffect hook takes two arguments:

  • A function that contains the side-effect logic.
     
  • An optional array of dependencies that determines when the side-effect function should be called.
     
useEffect(() => {
  // Side-effect logic
}, [dependencies]);
Get the tech career you deserve, faster!
Connect with our expert counsellors to understand how to hack your way to success
User rating 4.7/5
1:1 doubt support
95% placement record
Akash Pal
Senior Software Engineer
326% Hike After Job Bootcamp
Himanshu Gusain
Programmer Analyst
32 LPA After Job Bootcamp
After Job
Bootcamp

Ways of Controlling Side Effects in useEffect Hook

Running on Every Render (No Dependency Array)

If you want an effect to run after every render, you do not provide a second argument to useEffect.

useEffect(() => {
  console.log('This runs after every render');
});

Running Once on Mount (Empty Dependency Array)

To run an effect once when the component mounts, you provide an empty dependency array.

useEffect(() => {
  console.log('This runs once after the initial render, like componentDidMount');
}, []);

Running on Specific State or Props Changes (Dependency Array with Values)

When you want an effect to run only when certain values have changed, you include those values in the dependency array.

const [count, setCount] = useState(0);
useEffect(() => {
  console.log(`This runs when 'count' changes: ${count}`);
}, [count]);

Cleaning Up Side Effects

To prevent memory leaks or unwanted behavior, you can return a cleanup function from the effect.

useEffect(() => {
  const timer = setTimeout(() => {
    console.log('This effect has a timeout that needs to be cleared if the component unmounts');
  }, 1000);
  return () => {
    clearTimeout(timer);
    console.log('Cleanup function called, timer cleared');
  };
}, []);

Controlling Side Effects with Function Updates

Sometimes, you need to update the state based on the previous state within an effect. You can use a functional update to ensure you have the latest state.

const [count, setCount] = useState(0);
useEffect(() => {
  const interval = setInterval(() => {
    // Using a functional update ensures we always have the most recent state
    setCount(currentCount => currentCount + 1);
  }, 1000);
  return () => {
    clearInterval(interval);
    console.log('Interval cleared on cleanup');
  };
}, []); // Empty array means this effect setup and cleanup runs once

 

Also see,  React Native Reanimated

Ways to Mimic Lifecycle Methods Using useEffect Hook

For componentDidMount

To mimic componentDidMount, use an empty dependency array, ensuring the effect runs once after the component mounts:

useEffect(() => {
  // Code to run on component mount
}, []);

For componentDidUpdate

To mimic componentDidUpdate, include the state or props you want to watch in the dependency array:

useEffect(() => {
  // Code to run when dependencies update
}, [dependency1, dependency2]);

For componentWillUnmount

To mimic componentWillUnmount, return a cleanup function from within your effect:

useEffect(() => {
  // Setup code
  return () => {
    // Cleanup code, runs when the component unmounts
  };
}, []);

Advantages

  • Consolidation: It simplifies the codebase by replacing multiple lifecycle methods.
     
  • Optimization: It prevents unnecessary renders and side effects by using the dependency array.
     
  • Flexibility: It works with both state and props, making it versatile for various use cases.

Disadvantages

  • Complexity: It can be difficult to grasp, especially the rules around the dependency array.
     
  • Overuse: It can lead to performance issues if not used properly, such as forgetting to specify dependencies.

Practical Example

Let's consider a component that fetches user data from an API and subscribes to a chat service:

import React, { useState, useEffect } from 'react';

function UserProfile({ userId }) {
  const [userData, setUserData] = useState(null);

  useEffect(() => {
    // Fetch user data
    const fetchData = async () => {
      const response = await fetch(`/api/users/${userId}`);
      const data = await response.json();
      setUserData(data);
    };

    fetchData();

    // Subscribe to chat service
    const chatSubscription = ChatService.subscribe(userId);
    // Specify how to clean up after this effect
    return function cleanup() {
      ChatService.unsubscribe(chatSubscription);
    };
  }, [userId]); // Only re-run the effect if userId changes

  // Render user profile...
}

Must Read, React Native Paper

Frequently Asked Questions

Can useEffect be used for data fetching?

Absolutely, useEffect is ideal for data fetching. You can trigger a fetch request after the component mounts and update the state with the fetched data.

How do you prevent useEffect from running on every render?

By providing a dependency array. If it's empty, the effect runs once; if it includes variables, it runs whenever those variables change.

What's the purpose of the cleanup function in useEffect?

The cleanup function prevents memory leaks by cleaning up side effects (e.g., removing event listeners or canceling API requests) before the component unmounts or before the effect re-runs.

Conclusion

The useEffect hook is a potent feature of React that provides a streamlined and efficient way to handle side effects in functional components. By understanding its core principles and nuances, developers can write cleaner, more maintainable code. Whether you're managing API calls, subscriptions, or even timers, useEffect offers a declarative approach to orchestrating complex component behaviors. Embrace this hook, and you'll unlock a new level of proficiency in your React development.

You can refer to our guided paths on the Coding Ninjas. You can check our course to learn more about DSADBMSCompetitive ProgrammingPythonJavaJavaScript, etc. 

Also, check out some of the Guided Paths on topics such as Data Structure and AlgorithmsCompetitive ProgrammingOperating SystemsComputer Networks, DBMSSystem Design, etc., as well as some Contests, Test Series, and Interview Experiences curated by top Industry Experts.

Topics covered
1.
Introduction
2.
What is the useEffect Hook?
2.1.
Reason to Choose useEffect Hook
2.2.
Importing useEffect Hook
2.3.
Structure of useEffect Hook
3.
Ways of Controlling Side Effects in useEffect Hook
3.1.
Running on Every Render (No Dependency Array)
3.2.
Running Once on Mount (Empty Dependency Array)
3.3.
Running on Specific State or Props Changes (Dependency Array with Values)
3.4.
Cleaning Up Side Effects
3.5.
Controlling Side Effects with Function Updates
4.
Ways to Mimic Lifecycle Methods Using useEffect Hook
4.1.
For componentDidMount
4.2.
For componentDidUpdate
4.3.
For componentWillUnmount
5.
Advantages
6.
Disadvantages
7.
Practical Example
8.
Frequently Asked Questions
8.1.
Can useEffect be used for data fetching?
8.2.
How do you prevent useEffect from running on every render?
8.3.
What's the purpose of the cleanup function in useEffect?
9.
Conclusion