React 요약 6 - 조건부 렌더링과 리스트
Updated:
조건부 렌더링
function ConditionalRendering({ isLoggedIn, isAdmin, content }) {
// 1. if 문을 사용한 조건부 렌더링
if (!content) {
return <div>No content available</div>;
}
// 2. 삼항 연산자를 사용한 조건부 렌더링
return (
<div>
<h1>Welcome {isLoggedIn ? 'User' : 'Guest'}</h1>
{/* 3. 논리 연산자(&&)를 사용한 조건부 렌더링 */}
{isAdmin && <div className="admin-panel">Admin Panel</div>}
{/* 4. 즉시 실행 함수를 사용한 복잡한 조건부 렌더링 */}
{(() => {
if (isAdmin) return <div>Admin View</div>;
if (isLoggedIn) return <div>User View</div>;
return <div>Guest View</div>;
})()}
{/* 5. 객체를 사용한 조건부 렌더링 */}
{{
admin: <div>Admin Dashboard</div>,
user: <div>User Dashboard</div>,
guest: <div>Welcome, please log in</div>
}[isAdmin ? 'admin' : (isLoggedIn ? 'user' : 'guest')]}
<div>{content}</div>
</div>
);
}
코멘트: React에서는 다양한 방법으로 조건부 렌더링을 구현할 수 있습니다:
- if/else 문: 컴포넌트 전체를 조건부로 렌더링할 때 유용
- 삼항 연산자(?:): 간단한 조건부 렌더링에 적합
- 논리 연산자(&&): 조건이 참일 때만 요소를 렌더링할 때 유용
- 즉시 실행 함수: 복잡한 조건부 로직이 필요할 때 사용
- 객체 매핑: 여러 조건에 따라 다른 컴포넌트를 렌더링할 때 유용
상황에 맞는 방법을 선택하되, 가독성을 고려하는 것이 중요합니다.
리스트 렌더링
function ListRendering() {
const items = [
{ id: 1, name: 'Apple', category: 'Fruit' },
{ id: 2, name: 'Carrot', category: 'Vegetable' },
{ id: 3, name: 'Banana', category: 'Fruit' },
{ id: 4, name: 'Broccoli', category: 'Vegetable' }
];
return (
<div>
<h2>Item List</h2>
<ul>
{items.map(item => (
<li key={item.id}>
{item.name} - {item.category}
</li>
))}
</ul>
<h2>Grouped by Category</h2>
{/* 카테고리별로 그룹화하여 렌더링 */}
{Object.entries(
items.reduce((groups, item) => {
// 카테고리별로 그룹화
if (!groups[item.category]) {
groups[item.category] = [];
}
groups[item.category].push(item);
return groups;
}, {})
).map(([category, categoryItems]) => (
<div key={category}>
<h3>{category}</h3>
<ul>
{categoryItems.map(item => (
<li key={item.id}>{item.name}</li>
))}
</ul>
</div>
))}
</div>
);
}
코멘트: 리스트를 렌더링할 때는 항상 각 항목에 고유한
key
prop을 제공해야 합니다. 이는 React가 효율적으로 DOM을 업데이트하는 데 필요합니다. 가능하면 배열의 인덱스 대신 고유한 ID를 사용하세요. 인덱스를 key로 사용하면 항목의 순서가 변경될 때 예상치 못한 동작이 발생할 수 있습니다.
빈 상태와 로딩 상태 처리
function DataList({ data, isLoading, error }) {
// 로딩 상태 처리
if (isLoading) {
return (
<div className="loading-state">
<div className="spinner"></div>
<p>Loading data...</p>
</div>
);
}
// 에러 상태 처리
if (error) {
return (
<div className="error-state">
<p>Error: {error.message}</p>
<button onClick={retry}>Try Again</button>
</div>
);
}
// 빈 데이터 처리
if (!data || data.length === 0) {
return (
<div className="empty-state">
<p>No items found</p>
<button onClick={addNew}>Add New Item</button>
</div>
);
}
// 데이터가 있는 경우 렌더링
return (
<ul className="data-list">
{data.map(item => (
<li key={item.id}>{item.name}</li>
))}
</ul>
);
}
코멘트: 실제 애플리케이션에서는 데이터 로딩, 에러, 빈 상태 등 다양한 상태를 처리해야 합니다. 각 상태에 대해 적절한 UI를 제공하면 사용자 경험이 향상됩니다. 이러한 패턴을 “상태 기반 UI(State-based UI)”라고 하며, 데이터 페칭 라이브러리(React Query 등)와 함께 사용하면 더욱 효과적입니다.
Leave a comment