【问题标题】:React Component does not re-render on state change?React Component 不会在状态更改时重新渲染?
【发布时间】:2021-11-24 21:36:43
【问题描述】:

我正在更改排序顺序并按该顺序设置状态,但它不会自动重新呈现。 在函数 sortVal() 中,我设置了状态 setAllQues(sortArr1),它实际上将 allQues 数组设置为应该呈现的 sortArr1。但是,如果我单击排序按钮('Latest'、'A-Z'、'Z- A' 或 'Oldest ') 并且我在控制台记录它,数组 allQues 已完美排序但不会重新渲染。

const TopQuestions = () => {
const [allQues, setAllQues] = useState(null);
const [sortWay, setSortWay] = useState('Latest');
//const [sortArr, setSortArr] = useState([]);
const format1 = 'YYYY-MM-DD HH:mm:ss';

let sortArr1 = [];

useEffect(() => {
    fetch('http://localhost:4000/questions')
        .then(res => {
            return res.json();
        })
        .then(data => {
            if (sortWay === 'Latest') {
                data.sort((a, b) => b.sortOrder - a.sortOrder);
            }
            setAllQues(data);
        });
}, []);

const sortVal = val => {
    let sortArr1 = allQues;

    console.log(sortArr1, 'sortArr1');

    if (val === 'Latest') {
        sortArr1 && sortArr1.sort((a, b) => b.sortOrder - a.sortOrder);
        setAllQues(sortArr1);
    } else if (val === 'AZ') {
        sortArr1 && sortArr1.sort((a, b) => a.ques.localeCompare(b.ques));
        setAllQues(sortArr1);
    } else if (val === 'ZA') {
        sortArr1 && sortArr1.sort((a, b) => b.ques.localeCompare(a.ques));
        setAllQues(sortArr1);
    } else if (val === 'Oldest') {
        sortArr1 && sortArr1.sort((a, b) => a.sortOrder - b.sortOrder);
        setAllQues(sortArr1);
    }
    console.log(allQues, 'allQues');

};

    return (
    <div className='mx-56 pt-16 border-l-2'>
        <div className='px-4'>
            <div className='flex justify-between'>
                <div className=''>
                    <h1 className='text-3xl text-left mb-6 '>Top Questions</h1>
                </div>
                <div className='flex mb-6'>
                    <div className=' transition duration-300 ease-out border-2 border-r-0 border-gray-1050 px-2 py-1 hover:bg-gray-200 '>
                        <button
                            onClick={() => {
                                sortVal('Latest');
                            }}
                            className='text-gray-1150'
                        >
                            Latest
                        </button>
                    </div>
                    <div className=' transition duration-300 ease-out border-2 border-r-0 border-gray-1050 px-2 py-1 hover:bg-gray-200'>
                        <button
                            onClick={() => {
                                sortVal('AZ');
                            }}
                            className='text-gray-1150'
                        >
                            A-Z
                        </button>
                    </div>
                    <div className=' transition duration-300 ease-out border-2 border-r-0 border-gray-1050 px-2 py-1 hover:bg-gray-200 '>
                        <button
                            onClick={() => {
                                sortVal('ZA');
                            }}
                            className='text-gray-1150'
                        >
                            Z-A
                        </button>
                    </div>
                    <div className=' transition duration-300 ease-out border-2 border-gray-1050 px-2 py-1 hover:bg-gray-200 '>
                        <button
                            onClick={() => {
                                sortVal('Oldest');
                            }}
                            className='text-gray-1150'
                        >
                            Oldest
                        </button>
                    </div>
                </div>
            </div>

            {allQues &&
                allQues
                    .filter(allQue => (allQue.ques, allQue.author, allQue.dateTime))
                    .map(allQue => (
                        <EachQuestion
                            id={allQue.id}
                            ques={allQue.ques}
                            quesBrief={allQue.quesBrief}
                            author={allQue.author}
                            dateTime={allQue.dateTime}
                            hashes={allQue.hashes}
                        />
                    ))}
        </div>
    </div>
);

};

export default TopQuestions;

【问题讨论】:

  • Sort 同步排序,所以它是同一个数组。

标签: reactjs render setstate use-state


【解决方案1】:

不要直接对sortArr1进行排序,首先,对其进行复制,然后对该副本进行排序,然后将排序后的数组设置为状态。

你可以复制数组如下:

let copiedArr = [...sortArr1];
copiedArr.sort(sortFn);

setSortArr1(copiedArr);

【讨论】:

  • 出于这个目的本身,我使用了 sortArr1 来复制 allQues 的元素。
【解决方案2】:

也许您可以尝试将allQues 状态放在第二个useEffect 参数的数组依赖项上,因为它会监视allQues 的状态,然后当allQues 更改时,组件会对useEffect() 的第一个参数产生副作用

useEffect(() => {
    fetch('http://localhost:4000/questions')
        .then(res => {
            return res.json();
        })
        .then(data => {
            if (sortWay === 'Latest') {
                data.sort((a, b) => b.sortOrder - a.sortOrder);
            }
            setAllQues(data);
        });
}, [allQues]);

【讨论】:

  • 谢谢!那行得通。但是当我在 sortway 中设置默认排序方式为“最新”时,我还必须为 ex 设置 setSortWay('AZ'),以使其在 sortVal 函数中保持该状态。
猜你喜欢
  • 2018-11-29
  • 1970-01-01
  • 2020-10-03
  • 1970-01-01
  • 2018-03-17
  • 1970-01-01
  • 2019-02-27
相关资源
最近更新 更多