面试题答案
一键面试性能优化方面
- 减少渲染次数
- 使用 React.memo:对于函数式组件,通过
React.memo
包裹组件,它会对组件的 props 进行浅比较,如果 props 没有变化,组件将不会重新渲染。例如:
- 使用 React.memo:对于函数式组件,通过
const MyComponent = React.memo((props) => {
return <div>{props.value}</div>;
});
- **shouldComponentUpdate**:对于 class 组件,重写 `shouldComponentUpdate` 方法,在方法中自定义比较逻辑,只有当 props 或 state 变化满足特定条件时才重新渲染。
class MyClassComponent extends React.Component {
shouldComponentUpdate(nextProps, nextState) {
// 这里进行自定义比较逻辑,例如只比较某个 prop
return this.props.someProp!== nextProps.someProp;
}
render() {
return <div>{this.props.value}</div>;
}
}
- **使用 useCallback 和 useMemo**:`useCallback` 用于缓存函数,避免函数在每次渲染时重新创建,防止因函数引用变化导致子组件不必要的渲染。`useMemo` 用于缓存值,只有依赖项变化时才重新计算值。例如:
const ParentComponent = () => {
const [count, setCount] = useState(0);
const handleClick = useCallback(() => {
setCount(count + 1);
}, [count]);
const expensiveValue = useMemo(() => {
// 复杂计算逻辑
return count * count;
}, [count]);
return (
<div>
<ChildComponent onClick={handleClick} value={expensiveValue} />
</div>
);
};
- 优化内存使用
- 及时清理副作用:在使用
useEffect
时,返回清理函数,例如清除定时器、取消网络请求等,防止内存泄漏。
- 及时清理副作用:在使用
useEffect(() => {
const timer = setInterval(() => {
console.log('Interval running');
}, 1000);
return () => {
clearInterval(timer);
};
}, []);
- **避免不必要的对象创建**:在组件内部,尽量复用对象和数组,而不是每次渲染都创建新的实例。例如,将固定不变的配置对象提取到组件外部。
3. 优化数据获取
- 数据缓存:对于频繁请求且不经常变化的数据,可以在组件内部或全局进行缓存,避免重复请求。例如使用 useMemo
结合自定义缓存逻辑。
- 批量请求:如果有多个相关的数据请求,可以将它们合并为一个请求,减少网络开销。
打包策略方面
- 针对 Web 应用的打包
- 代码拆分:使用动态导入(
import()
)将组件库拆分成多个 chunk,根据实际使用情况按需加载,减少初始加载体积。例如:
- 代码拆分:使用动态导入(
const loadComponent = React.lazy(() => import('./MyComponent'));
function App() {
return (
<div>
<React.Suspense fallback={<div>Loading...</div>}>
<loadComponent />
</React.Suspense>
</div>
);
}
- **Tree - shaking**:利用 ES6 模块的静态分析特性,在打包过程中剔除未使用的代码,减小最终包的体积。确保组件库采用 ES6 模块规范编写,并且打包工具(如 Webpack)配置正确以支持 Tree - shaking。
- **优化图片和静态资源**:压缩图片,选择合适的图片格式(如 WebP),对于静态资源可以采用 CDN 加速,提高加载速度。
2. 针对 Node 应用的打包 - 使用 CommonJS 模块:由于 Node 主要使用 CommonJS 模块规范,在打包组件库供 Node 应用使用时,确保输出为 CommonJS 格式。可以通过打包工具(如 Webpack)进行相应的配置,将 ES6 模块转换为 CommonJS 模块。 - 排除浏览器特定代码:去除组件库中依赖的浏览器特定的 API 和代码,减少冗余。例如,如果组件库中包含一些 DOM 操作相关代码,在 Node 环境下是不需要的,应予以排除。 - 优化依赖管理:分析组件库在 Node 环境下的依赖,只打包必要的依赖,避免将一些在 Node 环境下不需要的前端依赖也打包进去,减小包体积。