React列表搜索输入框显示[object Object]筛选异常问题咨询
问题排查
你的代码存在3个直接导致异常的逻辑错误:
- 搜索输入框的
value错误绑定了存储村民列表的数组stateuserName,输入框仅接受字符串类型值,传入对象数组会被强制转换为[object Object]显示 - 筛选函数中无论关键词是否为空,最终都会执行
setUserName(people)将结果重置为全量数据,前面计算得到的筛选结果会被直接覆盖 - 列表渲染时遍历的是原始props传入的
people全量数组,而非存储筛选结果的state,即使筛选逻辑执行正确,页面也不会渲染匹配后的结果
关于JSON.stringify方案的判断
该思路不合理,存在三个明显缺陷:
- 性能损耗大:每次输入触发筛选都要对全量数据做序列化转换,数据量上升后会出现输入卡顿
- 匹配逻辑失控:序列化会遍历对象所有属性,用户输入任意属性名(比如
id、icon、personality)都会触发匹配,不符合按村民名称搜索的需求 - 匹配准确率低:序列化生成的字符串包含引号、括号等特殊字符,很容易出现预期外的匹配结果
修正后可直接运行的代码
import React, { useState } from "react"; import { Link } from "react-router-dom"; export default function Villagers({ people }) { // 单独维护搜索关键词的字符串state,和列表数据解耦 const [searchKeyword, setSearchKeyword] = useState(""); // 基于原始数据+搜索关键词直接派生筛选结果,无需重复存储列表state避免数据不一致 const displayList = people.filter((villager) => { const keyword = searchKeyword.trim().toLowerCase(); if (!keyword) return true; return villager.name["name-USen"].toLowerCase().startsWith(keyword); }); return ( <div> <div> <input type="search" value={searchKeyword} onChange={(e) => setSearchKeyword(e.target.value)} placeholder="输入村民名称搜索" /> </div> {displayList.map((villager) => { return ( <ul key={villager.id}> <Link to={`/villagers/${villager.id}`}> <li> <img src={villager.icon_uri} alt={villager.name["name-USen"]} /> {villager.name["name-USen"]} <br /> {villager.personality} </li> </Link> </ul> ); })} </div> ); }
核心修正点
- 拆分独立的字符串state存储输入框内容,从根源解决输入框显示异常的问题
- 移除筛选逻辑中强制重置全量数据的错误代码,通过计算属性得到筛选结果,避免多份state同步出错
- 列表渲染改为遍历筛选后的结果数组,输入关键词时页面会实时更新匹配内容
- 列表key优先使用数据自带的唯一id,替代索引作为key的潜在渲染问题
内容的提问来源于stack exchange,提问作者Elijah Prosperie
相关产品推荐
相关产品推荐

