Я новичок в React Hooks. Я пытаюсь отсортировать таблицу внутри React Hook, но после нажатия мой контент не обновляется. Это почему?

Это мой крючок:

const Main = ({ dataProps }) => {
const [data, setData] = useState(dataProps);
const sortById = (field) => {
        let sortedData = data.sort((a, b) => {
            if(a[field] < b[field]) { return -1; }
            if(a[field] > b[field]) { return 1; }
            return 0;
        });
        setData(sortedData);
};
return (
        <table>
            <thead>    
                <tr>
                    <th>iD <div className="arrows"><div onClick={() => sortById("id")} className="arrow-up"/></th>
                    <th>First name <div className="arrows"><div onClick={() => sortById("firstName")} className="arrow-up"/></div></th>
                </tr>
            </thead>
            <tbody>
            {data.map((user) => {
                return <tr key={user.id}>
                    <td className="number">{user.id}</td>
                    <td className="firstname">{user.firstName}</td>
                </tr>
            })}
            </tbody>
        </table>
);
};
0
John 29 Май 2019 в 17:09

2 ответа

Лучший ответ

sortById сортирует массив data. Но это не приводит к повторной визуализации компонента. field здесь, очевидно, является состоянием:

 const [data, setData] = useState(dataProps);      
 const [field, setField] = useState(null);

 const sorted = useMemo(() => {
   if(!field) return data;
   return data.slice().sort((a, b) => a[field].localeCompare(b[field]));
 }, [ data, field]);

 return <div>
   <a onClick={() => setField("firstName")}> Sort by Name</a>
   {sorted.map(/*...*/)}
</div>;
1
Jonas Wilms 29 Май 2019 в 14:15

Проблема заключается в сортировке, возвращающей тот же массив, который не вызывает повторного рендеринга если вы нарежете перед сортировкой, это решит проблему.

const sortById = (field) => {
        let sortedData = data.slice().sort((a, b) => {
            if(a[field] < b[field]) { return -1; }
            if(a[field] > b[field]) { return 1; }
            return 0;
        });
        setData(sortedData);
};

Кстати, более эффективный способ работы упоминается @ jonas-wilms

0
Amit Chauhan 29 Май 2019 в 14:19