You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何用useState&useEffect切换组件显示?Next.js长分类代码优化

优化车辆分类切换组件的方案

核心优化:移除冗余状态与副作用

你原来的多个useState(cars/bikes等)和useEffect完全是冗余的——只需要维护selectedCategory这一个状态,直接用它判断要渲染的组件即可,无需额外同步多个状态。

用配置化方式实现可扩展的分类管理

把分类信息抽象成配置数组/对象,新增分类时只需在配置里加一项,不用修改渲染逻辑,彻底解决代码冗余问题。

优化后的完整代码(配置数组版)

import Cars from './Cars';
import Bikes from './Bikes';
import Motorcycles from './Motorcycles';
import Scooters from './Scooters';
import { useState } from 'react';

const Vehicles = () => {
  const [selectedCategory, setSelectedCategory] = useState("cars");

  // 统一管理分类的标识、显示名称和对应组件
  const categoryConfig = [
    { key: "cars", label: "Cars", Component: Cars },
    { key: "bikes", label: "Bikes", Component: Bikes },
    { key: "motorcycles", label: "Motorcycles", Component: Motorcycles },
    { key: "scooters", label: "Scooters", Component: Scooters },
  ];

  return (
    <div>
      {/* 遍历配置生成切换按钮 */}
      <div>
        {categoryConfig.map(({ key, label }) => (
          <button
            key={key}
            onClick={() => setSelectedCategory(key)}
            {/* 可选:给当前选中按钮加高亮样式 */}
            style={{ backgroundColor: selectedCategory === key ? '#e0e0e0' : 'transparent' }}
          >
            {label}
          </button>
        ))}
      </div>

      {/* 渲染当前选中的分类组件 */}
      <div>
        {categoryConfig.find(item => item.key === selectedCategory)?.Component && (
          <categoryConfig.find(item => item.key === selectedCategory).Component />
        )}
      </div>
    </div>
  );
};

export default Vehicles;

简化版:对象映射实现快速匹配

如果觉得数组find有点冗余,可以用对象映射直接定位组件:

import Cars from './Cars';
import Bikes from './Bikes';
import Motorcycles from './Motorcycles';
import Scooters from './Scooters';
import { useState } from 'react';

const Vehicles = () => {
  const [selectedCategory, setSelectedCategory] = useState("cars");

  // 组件与分类标识的映射表
  const categoryComponents = {
    cars: Cars,
    bikes: Bikes,
    motorcycles: Motorcycles,
    scooters: Scooters,
  };
  // 分类标识与显示名称的映射表
  const categoryLabels = {
    cars: "Cars",
    bikes: "Bikes",
    motorcycles: "Motorcycles",
    scooters: "Scooters",
  };

  const CurrentComponent = categoryComponents[selectedCategory];

  return (
    <div>
      <div>
        {Object.entries(categoryLabels).map(([key, label]) => (
          <button
            key={key}
            onClick={() => setSelectedCategory(key)}
            style={{ backgroundColor: selectedCategory === key ? '#e0e0e0' : 'transparent' }}
          >
            {label}
          </button>
        ))}
      </div>

      {CurrentComponent && <CurrentComponent />}
    </div>
  );
};

export default Vehicles;

其他可选方案

  • Next.js 路由集成:如果希望每个分类对应独立URL(比如/vehicles/cars),可以用Next.js动态路由(pages/vehicles/[category].js),通过URL参数控制显示分类,还支持页面刷新、书签分享。
  • useReducer(可选):如果后续分类逻辑变得复杂(比如批量更新、异步数据处理),可以用useReducer管理状态,但当前场景下属于过度设计。

内容的提问来源于stack exchange,提问作者Mintee

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.22 06:39:15