REACT INTERVIEW QUESTIONS - 2 YEARS EXPERIENCE
1. REACT FUNDAMENTALS
Q: What is React and what are its key features?
A:
React is a JavaScript library for building user interfaces, particularly single-
page applications.
Key Features:
- Virtual DOM for efficient rendering
- Component-based architecture
- JSX for writing HTML-like code in JavaScript
- Unidirectional data flow
- Cross-platform (React Native for mobile)
Example:
```jsx
import React from 'react';
function App() {
return (
<div className="App">
<h1>Hello React!</h1>
</div>
);
}
export default App;
```
Q: Explain JSX and its benefits
A:
JSX is a syntax extension for JavaScript that allows you to write HTML-like code in
JavaScript.
Benefits:
- Familiar HTML-like syntax
- Better error detection at compile time
- Prevents XSS attacks
- Easier to understand and maintain
Example:
```jsx
// JSX
const element = <h1>Hello, {name}!</h1>;
// Compiled to JavaScript
const element = React.createElement('h1', null, 'Hello, ', name, '!');
// Conditional rendering in JSX
function Greeting({ isLoggedIn }) {
return (
<div>
{isLoggedIn ? <h1>Welcome back!</h1> : <h1>Please log in.</h1>}
</div>
);
}
```
2. COMPONENTS AND PROPS
Q: What are components in React and what are the different types?
A:
Components are reusable UI pieces that can be composed together.
Types:
- Functional Components (recommended)
- Class Components (legacy)
Example:
```jsx
// Functional Component
function Welcome(props) {
return <h1>Hello, {props.name}!</h1>;
}
// Class Component
class Welcome extends React.Component {
render() {
return <h1>Hello, {this.props.name}!</h1>;
}
}
// Usage
<Welcome name="John" />
```
Q: Explain props and how to pass data between components
A:
Props are read-only properties passed from parent to child components.
Example:
```jsx
// Parent Component
function ParentComponent() {
const user = {
name: 'John Doe',
age: 30,
email: 'john@example.com'
};
return (
<div>
<ChildComponent
name={user.name}
age={user.age}
email={user.email}
onUserClick={() => console.log('User clicked')}
/>
</div>
);
}
// Child Component
function ChildComponent({ name, age, email, onUserClick }) {
return (
<div onClick={onUserClick}>
<h2>{name}</h2>
<p>Age: {age}</p>
<p>Email: {email}</p>
</div>
);
}
```
3. STATE AND LIFECYCLE
Q: What is state in React and how do you manage it?
A:
State is a component's internal data that can change over time and triggers re-
renders.
Example:
```jsx
import React, { useState } from 'react';
function Counter() {
const [count, setCount] = useState(0);
const [name, setName] = useState('');
const increment = () => {
setCount(count + 1);
};
const decrement = () => {
setCount(count - 1);
};
return (
<div>
<h2>Count: {count}</h2>
<button onClick={increment}>Increment</button>
<button onClick={decrement}>Decrement</button>
<input
value={name}
onChange={(e) => setName(e.target.value)}
placeholder="Enter your name"
/>
<p>Hello, {name}!</p>
</div>
);
}
```
Q: Explain useEffect hook and its use cases
A:
useEffect is a hook that lets you perform side effects in functional components.
Example:
```jsx
import React, { useState, useEffect } from 'react';
function UserProfile({ userId }) {
const [user, setUser] = useState(null);
const [loading, setLoading] = useState(true);
// Fetch user data when component mounts or userId changes
useEffect(() => {
const fetchUser = async () => {
setLoading(true);
try {
const response = await fetch(`/api/users/${userId}`);
const userData = await response.json();
setUser(userData);
} catch (error) {
console.error('Error fetching user:', error);
} finally {
setLoading(false);
}
};
fetchUser();
}, [userId]); // Dependency array
// Cleanup function
useEffect(() => {
const timer = setInterval(() => {
console.log('Timer tick');
}, 1000);
return () => {
clearInterval(timer); // Cleanup on unmount
};
}, []);
if (loading) return <div>Loading...</div>;
if (!user) return <div>User not found</div>;
return (
<div>
<h2>{user.name}</h2>
<p>{user.email}</p>
</div>
);
}
```
4. EVENT HANDLING
Q: How do you handle events in React?
A:
React events are handled using camelCase event handlers and synthetic events.
Example:
```jsx
import React, { useState } from 'react';
function EventHandling() {
const [formData, setFormData] = useState({
username: '',
email: ''
});
const handleInputChange = (e) => {
const { name, value } = e.target;
setFormData(prev => ({
...prev,
[name]: value
}));
};
const handleSubmit = (e) => {
e.preventDefault(); // Prevent default form submission
console.log('Form submitted:', formData);
};
const handleClick = (e, id) => {
console.log('Button clicked:', id);
};
return (
<form onSubmit={handleSubmit}>
<input
type="text"
name="username"
value={formData.username}
onChange={handleInputChange}
placeholder="Username"
/>
<input
type="email"
name="email"
value={formData.email}
onChange={handleInputChange}
placeholder="Email"
/>
<button type="submit">Submit</button>
<button
type="button"
onClick={(e) => handleClick(e, 'custom-button')}
>
Custom Button
</button>
</form>
);
}
```
5. CONDITIONAL RENDERING
Q: How do you implement conditional rendering in React?
A:
Conditional rendering can be done using if statements, ternary operators, and
logical operators.
Example:
```jsx
import React, { useState } from 'react';
function ConditionalRendering() {
const [isLoggedIn, setIsLoggedIn] = useState(false);
const [userRole, setUserRole] = useState('user');
const [showDetails, setShowDetails] = useState(false);
// Method 1: Ternary operator
const renderGreeting = () => {
return isLoggedIn ? <h1>Welcome back!</h1> : <h1>Please log in</h1>;
};
// Method 2: Logical AND operator
const renderAdminPanel = () => {
return isLoggedIn && userRole === 'admin' && <div>Admin Panel</div>;
};
// Method 3: Multiple conditions
const renderContent = () => {
if (!isLoggedIn) {
return <div>Please log in to continue</div>;
}
if (userRole === 'admin') {
return <div>Admin Dashboard</div>;
}
return <div>User Dashboard</div>;
};
return (
<div>
{renderGreeting()}
{renderAdminPanel()}
{renderContent()}
{/* Inline conditional rendering */}
{showDetails && (
<div>
<p>Additional details here...</p>
</div>
)}
<button onClick={() => setIsLoggedIn(!isLoggedIn)}>
{isLoggedIn ? 'Logout' : 'Login'}
</button>
<button onClick={() => setShowDetails(!showDetails)}>
{showDetails ? 'Hide' : 'Show'} Details
</button>
</div>
);
}
```
6. LISTS AND KEYS
Q: How do you render lists in React and why are keys important?
A:
Lists are rendered using map() and keys help React identify which items have
changed.
Example:
```jsx
import React, { useState } from 'react';
function TodoList() {
const [todos, setTodos] = useState([
{ id: 1, text: 'Learn React', completed: false },
{ id: 2, text: 'Build a project', completed: false },
{ id: 3, text: 'Deploy to production', completed: false }
]);
const toggleTodo = (id) => {
setTodos(prev =>
prev.map(todo =>
todo.id === id
? { ...todo, completed: !todo.completed }
: todo
)
);
};
const addTodo = (text) => {
const newTodo = {
id: Date.now(), // Simple ID generation
text,
completed: false
};
setTodos(prev => [...prev, newTodo]);
};
return (
<div>
<h2>Todo List</h2>
{/* Rendering list with keys */}
<ul>
{todos.map(todo => (
<li
key={todo.id} // Unique key for each item
onClick={() => toggleTodo(todo.id)}
style={{
textDecoration: todo.completed ? 'line-through' : 'none',
cursor: 'pointer'
}}
>
{todo.text}
</li>
))}
</ul>
{/* Adding new todo */}
<button onClick={() => addTodo('New task')}>
Add Todo
</button>
</div>
);
}
// Example with more complex list rendering
function UserList({ users }) {
return (
<div>
{users.map((user, index) => (
<div key={user.id} className="user-card">
<h3>{user.name}</h3>
<p>{user.email}</p>
<span>Index: {index}</span>
</div>
))}
</div>
);
}
```
7. FORMS AND CONTROLLED COMPONENTS
Q: What are controlled components and how do you handle forms?
A:
Controlled components have their value controlled by React state.
Example:
```jsx
import React, { useState } from 'react';
function ControlledForm() {
const [formData, setFormData] = useState({
username: '',
email: '',
password: '',
agree: false,
country: 'us'
});
const [errors, setErrors] = useState({});
const handleChange = (e) => {
const { name, value, type, checked } = e.target;
setFormData(prev => ({
...prev,
[name]: type === 'checkbox' ? checked : value
}));
// Clear error when user starts typing
if (errors[name]) {
setErrors(prev => ({
...prev,
[name]: ''
}));
}
};
const validateForm = () => {
const newErrors = {};
if (!formData.username.trim()) {
newErrors.username = 'Username is required';
}
if (!formData.email.includes('@')) {
newErrors.email = 'Valid email is required';
}
if (formData.password.length < 6) {
newErrors.password = 'Password must be at least 6 characters';
}
if (!formData.agree) {
newErrors.agree = 'You must agree to terms';
}
setErrors(newErrors);
return Object.keys(newErrors).length === 0;
};
const handleSubmit = (e) => {
e.preventDefault();
if (validateForm()) {
console.log('Form submitted:', formData);
// Submit form data
}
};
return (
<form onSubmit={handleSubmit}>
<div>
<label>Username:</label>
<input
type="text"
name="username"
value={formData.username}
onChange={handleChange}
/>
{errors.username && <span className="error">{errors.username}</span>}
</div>
<div>
<label>Email:</label>
<input
type="email"
name="email"
value={formData.email}
onChange={handleChange}
/>
{errors.email && <span className="error">{errors.email}</span>}
</div>
<div>
<label>Password:</label>
<input
type="password"
name="password"
value={formData.password}
onChange={handleChange}
/>
{errors.password && <span className="error">{errors.password}</span>}
</div>
<div>
<label>Country:</label>
<select
name="country"
value={formData.country}
onChange={handleChange}
>
<option value="us">United States</option>
<option value="uk">United Kingdom</option>
<option value="ca">Canada</option>
</select>
</div>
<div>
<label>
<input
type="checkbox"
name="agree"
checked={formData.agree}
onChange={handleChange}
/>
I agree to the terms
</label>
{errors.agree && <span className="error">{errors.agree}</span>}
</div>
<button type="submit">Submit</button>
</form>
);
}
```
8. COMPONENT COMPOSITION
Q: How do you compose components and pass children?
A:
Component composition allows you to build complex UIs from simple components.
Example:
```jsx
import React from 'react';
// Layout components
function Header({ children }) {
return (
<header style={{ padding: '1rem', backgroundColor: '#f0f0f0' }}>
{children}
</header>
);
}
function Sidebar({ children }) {
return (
<aside style={{ width: '200px', backgroundColor: '#e0e0e0' }}>
{children}
</aside>
);
}
function Main({ children }) {
return (
<main style={{ flex: 1, padding: '1rem' }}>
{children}
</main>
);
}
// Reusable components
function Button({ children, onClick, variant = 'primary' }) {
const styles = {
primary: { backgroundColor: 'blue', color: 'white' },
secondary: { backgroundColor: 'gray', color: 'white' },
danger: { backgroundColor: 'red', color: 'white' }
};
return (
<button
onClick={onClick}
style={{
padding: '0.5rem 1rem',
border: 'none',
borderRadius: '4px',
cursor: 'pointer',
...styles[variant]
}}
>
{children}
</button>
);
}
function Card({ title, children }) {
return (
<div style={{
border: '1px solid #ccc',
borderRadius: '8px',
padding: '1rem',
margin: '1rem 0'
}}>
{title && <h3>{title}</h3>}
{children}
</div>
);
}
// Main App component using composition
function App() {
return (
<div style={{ display: 'flex', minHeight: '100vh' }}>
<Sidebar>
<h3>Navigation</h3>
<ul>
<li>Dashboard</li>
<li>Users</li>
<li>Settings</li>
</ul>
</Sidebar>
<div style={{ flex: 1, display: 'flex', flexDirection: 'column' }}>
<Header>
<h1>My Application</h1>
<Button onClick={() => console.log('Logout')} variant="secondary">
Logout
</Button>
</Header>
<Main>
<Card title="Welcome">
<p>This is the main content area.</p>
<Button onClick={() => console.log('Primary action')}>
Primary Action
</Button>
<Button onClick={() => console.log('Danger action')} variant="danger">
Delete
</Button>
</Card>
<Card>
<p>Another card without a title.</p>
</Card>
</Main>
</div>
</div>
);
}
```
9. ERROR BOUNDARIES
Q: What are Error Boundaries and how do you implement them?
A:
Error Boundaries catch JavaScript errors anywhere in the component tree and display
a fallback UI.
Example:
```jsx
import React from 'react';
class ErrorBoundary extends React.Component {
constructor(props) {
super(props);
this.state = { hasError: false, error: null };
}
static getDerivedStateFromError(error) {
return { hasError: true, error };
}
componentDidCatch(error, errorInfo) {
console.error('Error caught by boundary:', error, errorInfo);
// Log error to service
}
render() {
if (this.state.hasError) {
return (
<div style={{
padding: '2rem',
textAlign: 'center',
backgroundColor: '#fff3cd',
border: '1px solid #ffeaa7'
}}>
<h2>Something went wrong!</h2>
<p>We're sorry, but something unexpected happened.</p>
<button
onClick={() => this.setState({ hasError: false })}
style={{
padding: '0.5rem 1rem',
backgroundColor: '#007bff',
color: 'white',
border: 'none',
borderRadius: '4px',
cursor: 'pointer'
}}
>
Try Again
</button>
</div>
);
}
return this.props.children;
}
}
// Component that might throw an error
function BuggyComponent({ shouldThrow }) {
if (shouldThrow) {
throw new Error('This is a test error');
}
return <div>This component works fine!</div>;
}
// Usage
function App() {
const [shouldThrow, setShouldThrow] = React.useState(false);
return (
<div>
<ErrorBoundary>
<BuggyComponent shouldThrow={shouldThrow} />
</ErrorBoundary>
<button onClick={() => setShouldThrow(!shouldThrow)}>
{shouldThrow ? 'Fix Component' : 'Break Component'}
</button>
</div>
);
}
```
10. PRACTICAL CODING EXERCISES
Q: Create a simple counter with increment, decrement, and reset functionality
A:
```jsx
import React, { useState } from 'react';
function Counter() {
const [count, setCount] = useState(0);
const increment = () => setCount(prev => prev + 1);
const decrement = () => setCount(prev => prev - 1);
const reset = () => setCount(0);
return (
<div style={{ textAlign: 'center', padding: '2rem' }}>
<h2>Counter: {count}</h2>
<div style={{ display: 'flex', gap: '1rem', justifyContent: 'center' }}>
<button onClick={decrement}>-</button>
<button onClick={reset}>Reset</button>
<button onClick={increment}>+</button>
</div>
</div>
);
}
```
Q: Create a todo list with add, delete, and toggle functionality
A:
```jsx
import React, { useState } from 'react';
function TodoList() {
const [todos, setTodos] = useState([]);
const [inputValue, setInputValue] = useState('');
const addTodo = (e) => {
e.preventDefault();
if (inputValue.trim()) {
setTodos(prev => [...prev, {
id: Date.now(),
text: inputValue.trim(),
completed: false
}]);
setInputValue('');
}
};
const toggleTodo = (id) => {
setTodos(prev =>
prev.map(todo =>
todo.id === id
? { ...todo, completed: !todo.completed }
: todo
)
);
};
const deleteTodo = (id) => {
setTodos(prev => prev.filter(todo => todo.id !== id));
};
return (
<div style={{ maxWidth: '400px', margin: '0 auto', padding: '2rem' }}>
<h2>Todo List</h2>
<form onSubmit={addTodo}>
<input
type="text"
value={inputValue}
onChange={(e) => setInputValue(e.target.value)}
placeholder="Add a new todo..."
style={{ width: '100%', padding: '0.5rem', marginBottom: '1rem' }}
/>
<button type="submit">Add Todo</button>
</form>
<ul style={{ listStyle: 'none', padding: 0 }}>
{todos.map(todo => (
<li
key={todo.id}
style={{
display: 'flex',
alignItems: 'center',
padding: '0.5rem',
borderBottom: '1px solid #eee'
}}
>
<input
type="checkbox"
checked={todo.completed}
onChange={() => toggleTodo(todo.id)}
/>
<span
style={{
flex: 1,
marginLeft: '0.5rem',
textDecoration: todo.completed ? 'line-through' : 'none'
}}
>
{todo.text}
</span>
<button
onClick={() => deleteTodo(todo.id)}
style={{
backgroundColor: 'red',
color: 'white',
border: 'none',
padding: '0.25rem 0.5rem',
cursor: 'pointer'
}}
>
Delete
</button>
</li>
))}
</ul>
</div>
);
}
```
COMMON INTERVIEW TIPS FOR 2 YEARS EXPERIENCE:
- Focus on understanding React fundamentals
- Practice building simple components
- Understand state management with useState
- Know how to handle forms and events
- Be comfortable with conditional rendering
- Understand component composition
- Practice with lists and keys
- Know basic error handling
- Be able to explain JSX and props
- Understand the component lifecycle with useEffect