上周折腾React花了两天时间,记录一下过程,下次再搞就不用重新查了。
安装
# 用 Vite 创建项目(比 CRA 快很多)
npm create vite@latest my-app -- --template react-ts
cd my-app
npm install
npm run dev
# 常用依赖
npm install react-router-dom zustand axios常用代码片段
// 自定义 Hook:防抖请求
import { useState, useEffect, useCallback } from "react";
function useDebounceSearch(delay = 300) {
const [keyword, setKeyword] = useState("");
const [results, setResults] = useState([]);
const [loading, setLoading] = useState(false);
useEffect(() => {
if (!keyword.trim()) {
setResults([]);
return;
}
const timer = setTimeout(async () => {
setLoading(true);
try {
const res = await fetch(\`/api/search?q=\${keyword}\`);
const data = await res.json();
setResults(data);
} catch (e) {
console.error("搜索失败", e);
} finally {
setLoading(false);
}
}, delay);
return () => clearTimeout(timer);
}, [keyword, delay]);
return { keyword, setKeyword, results, loading };
}
// 使用
function SearchBox() {
const { keyword, setKeyword, results, loading } = useDebounceSearch();
return (
<div>
<input value={keyword} onChange={e => setKeyword(e.target.value)} placeholder="搜索..." />
{loading && <span>加载中...</span>}
<ul>{results.map(r => <li key={r.id}>{r.title}</li>)}</ul>
</div>
);
}日常小技巧
- useEffect 的依赖数组别偷懒写 [],该加的不加会导致 stale closure
- key 用稳定 ID,别用 index,列表增删的时候会出 bug
- React.memo 用在渲染成本高的组件上,别啥都 memo
- 状态能往下放就往下放,别全塞 Context 里,一个更新全部重渲染
一个实际例子
之前一个列表页渲染5万条数据,直接卡死了。后来看了 Dan Abramov 的视频,用虚拟列表(react-window)只渲染可见区域,滚动丝滑得很。关键代码就几行。
常见问题
useEffect 无限循环怎么破?
90% 是依赖数组里放了对象或函数引用。把对象用 useMemo 包一层,函数用 useCallback。或者把依赖移到 effect 里面。
组件太大了怎么拆?
按职责拆:数据获取一个组件,展示一个组件,交互逻辑抽成自定义 Hook。一个组件超过 200 行就该考虑拆了。
React 和 Vue 怎么选?
别纠结,都能干活。团队熟悉哪个用哪个。React 生态大,Vue 上手快。要是做中后台,Vue + Element 可能更快出活。
先写到这,后面有新发现再更新。觉得有用的话收藏一下。
0 条评论 欢迎参与讨论