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

Next.js如何通过两个按钮对props传入的商品数据按价格排序

实现逻辑修正

你的代码核心问题有3个:

  • 单独提取price字段存入state排序,丢失了商品条目其余的id、名称、图片等属性
  • 直接调用数组原生sort()方法会修改原数组,会意外篡改props传入的源数据
  • 现有useEffect逻辑完全冗余,排序操作不需要监听state二次触发

完整可运行代码

Products组件修改

import { useState } from 'react'
import Filter from './Filter' // 替换为你项目中Filter组件的实际路径

function Products({ data }) {
  // state存储完整的商品数组,初始值对props数据做浅拷贝,避免修改原数据
  const [productList, setProductList] = useState([...data])

  // 价格从高到低排序
  const handleHigh = () => {
    // 先拷贝原数组再执行排序,不修改源数据
    const sorted = [...data].sort((prev, next) => next.price - prev.price)
    setProductList(sorted)
  }

  // 价格从低到高排序
  const handleLow = () => {
    const sorted = [...data].sort((prev, next) => prev.price - next.price)
    setProductList(sorted)
  }

  return (
    <div>
      {/* 把排序方法传入Filter组件 */}
      <Filter handleHigh={handleHigh} handleLow={handleLow} />
      
      {/* 遍历排序后的完整商品数组渲染 */}
      <div className="product-list">
        {productList.map(product => (
          <div key={product.id} className="product-item">
            {/* 可以直接访问商品的所有属性,不会丢失字段 */}
            <h3>{product.name}</h3>
            <p>价格:¥{product.price}</p>
          </div>
        ))}
      </div>
    </div>
  )
}

export default Products

Filter组件说明

你现有的Filter组件不需要做任何修改,只要保证在Products组件中正确引入、传入两个排序回调函数即可正常使用。


关键逻辑说明
  • 排序时直接操作完整商品对象数组,仅在sort比较函数中取两个商品的price字段做数值对比,排序后保留商品全部属性
  • 每次排序前都通过展开运算符[...data]创建原数组的浅拷贝,避免sort方法直接修改props传入的只读源数据
  • 移除了冗余的useEffect监听,点击按钮时直接计算排序结果更新state,减少不必要的重渲染

内容的提问来源于stack exchange,提问作者Francisco José López Laperal

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.08.30 17:12:29