简体   繁体   English

在 React 中 state 更改后功能组件未重新渲染

[英]functional component is not re-rendering after state change in React

I have a functional component that retrieves data from an http request on page load and updates the state to store that data using useState.我有一个功能组件,它在页面加载时从 http 请求中检索数据,并更新 state 以使用 useState 存储该数据。 I then try to map out a nested array (polls.pollOptions) from the data, I get an error: " TypeError: Cannot read property 'map' of undefined ".然后我尝试 map 从数据中取出一个嵌套数组 (polls.pollOptions),我收到一个错误:“ TypeError: Cannot read property 'map' of undefined ”。 If i remove the map function and check the React component extension, I can see that the state was updated and it has the correct data.如果我删除 map function 并检查 React 组件扩展,我可以看到 state 已更新并且它具有正确的数据。 So why doesn't this render to the screen & why receive an error when the data is there to map through?那么为什么这不会呈现到屏幕上,为什么当数据通过 map 时会收到错误消息? Heres my component:这是我的组件:

import React, { useState, useEffect } from "react";
import axios from "axios";
import { useParams } from "react-router";

export const EditPolls2 = () => {
  const { _id } = useParams();
  const [polls, setPolls] = useState([]);

  useEffect(() => {
    axios.get(`/polls/${_id}`).then((p) => {
      setPolls(p.data);
    });
  }, [_id]);

  return (
    <div>
      <p>edit polls 2</p>
      <div>
        <ul>
          {polls.pollOptions.map((p) => (
            <li key={p.pollId}>{p.option}</li>
          ))}
        </ul>
      </div>
    </div>
  );
};

Your current initial state is an empty array, and you are trying to access pollOptions , which is a property that doesn't exist on an empty array.您当前的初始 state 是一个空数组,您正在尝试访问pollOptions ,这是一个在空数组上不存在的属性。

If you don't need anything, but pollOptions , leave the initial state as an empty array, use polls and not polls.pollOptions when mapping the data, and make sure to set pollOptions as the state:如果您不需要任何东西,但pollOptions ,请将初始 state 保留为空数组,在映射数据时使用polls而不是polls.pollOptions ,并确保将pollOptions设置为 state:

export const EditPolls2 = () => {
  const { _id } = useParams();
  const [polls, setPolls] = useState([]);

  useEffect(() => {
    axios.get(`/polls/${_id}`).then((p) => {
      setPolls(p.data.pollOptions); // set the pollOptions array as the state
    });
  }, [_id]);

  return (
    <div>
      <p>edit polls 2</p>
      <div>
        <ul>
          {polls.map((p) => ( // use polls and not pollOptions
            <li key={p.pollId}>{p.option}</li>
          ))}
        </ul>
      </div>
    </div>
  );
};

If you do need the entire object ( data ) in the state, don't use initial state, and use optional chaining ( ?. ) when mapping the array.如果您确实需要 state 中的整个 object ( data ),请不要使用初始 state,并在映射数组时使用可选链接 ( ?. ) If the state is undefined , the mapping would be skipped:如果 state undefined ,则将跳过映射:

export const EditPolls2 = () => {
  const { _id } = useParams();
  const [polls, setPolls] = useState(); // no initial state

  useEffect(() => {
    axios.get(`/polls/${_id}`).then((p) => {
      setPolls(p.data);
    });
  }, [_id]);

  return (
    <div>
      <p>edit polls 2</p>
      <div>
        <ul>
          {polls.pollOptions?.map((p) => ( // optional chaining
            <li key={p.pollId}>{p.option}</li>
          ))}
        </ul>
      </div>
    </div>
  );
};

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM