【问题标题】:How to fix "TypeError: results.map is not a function", in React如何在 React 中修复“TypeError:results.map 不是函数”
【发布时间】:2020-02-09 02:56:07
【问题描述】:
function Results(props) {
  var results = props.results;
  return (
    <>
      <table>
        <thead>
          <tr>
            <th>Book Name</th>
            <th>Author</th>
            <th>S.no</th>
            <th>Series Name</th>
            <th>Type</th>
            <th>Genre</th>
            <th>Kindle/Real</th>
          </tr>
        </thead>
        <tbody>
          {results.map(result => {
            return (
              <tr key={result.name}>
                <td>{result.name}</td>
                <td>{result.author}</td>
                <td>{result.sno}</td>
                <td>{result.series}</td>
                <td>{result.type}</td>
                <td>{result.genre}</td>
                <td>{result.kindeReal}</td>
              </tr>
            );
          })}
        </tbody>
      </table>
    </>
  );
}

当我尝试渲染上面的 com 组件时,我得到了错误:

TypeError: results.map 不是函数

结果变量是一个对象数组,类似于:

[{"type":1},{"type":0},{"type":2}]

但是,当我使用 .map 函数时,它会返回错误!明明是数组,为什么我不能用呢?

这是 console.log(results) 的输出。

[{"Book_Name":"Time Riders","Author":"Alex Scarrow","S_no":1,"Series_Name":"Time Riders","Fiction_Non_fiction_Companion_Prequel":"Fiction","Genre":"Sci-fi/Mystery/Thriller","Kindle_Real":"Real"},{"Book_Name":"Day of the Predator ","Author":"Alex Scarrow","S_no":2,"Series_Name":"Time Riders","Fiction_Non_fiction_Companion_Prequel":"Fiction","Genre":"Sci-fi/Mystery/Thriller","Kindle_Real":"Real"},{"Book_Name":"The Doomsday Code","Author":"Alex Scarrow","S_no":3,"Series_Name":"Time Riders","Fiction_Non_fiction_Companion_Prequel":"Fiction","Genre":"Sci-fi/Mystery/Thriller","Kindle_Real":"Real"},{"Book_Name":"The Eternal War","Author":"Alex Scarrow","S_no":4,"Series_Name":"Time Riders","Fiction_Non_fiction_Companion_Prequel":"Fiction","Genre":"Sci-fi/Mystery/Thriller","Kindle_Real":"Real"},{"Book_Name":"Gates of Rome","Author":"Alex Scarrow","S_no":5,"Series_Name":"Time Riders","Fiction_Non_fiction_Companion_Prequel":"Fiction","Genre":"Sci-fi/Mystery/Thriller","Kindle_Real":"Real"},{"Book_Name":"City of Shadows","Author":"Alex Scarrow","S_no":6,"Series_Name":"Time Riders","Fiction_Non_fiction_Companion_Prequel":"Fiction","Genre":"Sci-fi/Mystery/Thriller","Kindle_Real":"Real"},{"Book_Name":"The Pirate Kings","Author":"Alex Scarrow","S_no":7,"Series_Name":"Time Riders","Fiction_Non_fiction_Companion_Prequel":"Fiction","Genre":"Sci-fi/Mystery/Thriller","Kindle_Real":"Real"},{"Book_Name":"The Mayan Prophecy","Author":"Alex Scarrow","S_no":8,"Series_Name":"Time Riders","Fiction_Non_fiction_Companion_Prequel":"Fiction","Genre":"Sci-fi/Mystery/Thriller","Kindle_Real":"Real"},{"Book_Name":"The Infinity Cage","Author":"Alex Scarrow","S_no":9,"Series_Name":"Time Riders","Fiction_Non_fiction_Companion_Prequel":"Fiction","Genre":"Sci-fi/Mystery/Thriller","Kindle_Real":"Real"}]

对我来说它看起来像一个数组。那为什么不是数组呢?

这是父组件。

import React from "react";
import Results from "./results";

function ResultsRenderer(props) {
  if (props.status === true) {
    return <Results results={props.results} />;
  } else {
    return <>{"No"}</>;
  }
}

export default ResultsRenderer;

这是 ResultsRenderer 的父组件。

import React, { useState } from "react";
import { useEffect } from "react";
import "bootstrap/dist/css/bootstrap.min.css";
import Form from "./searcherFormDumb";
import { toast } from "react-toastify";
import ResultsRenderer from "./resultsRenderer";

function Searcher() {
  const [answer, setAnswer] = useState(["Empty", false]);
  const [book, setBook] = useState({
    name: "",
    author: "",
    sno: null,
    series: "",
    type: "",
    genre: "",
    kindleReal: ""
  });
  const defaultState = {
    name: "",
    author: "",
    sno: null,
    series: "",
    type: "",
    genre: "",
    kindleReal: ""
  };

  function handleChange(event) {
    const updatedBook = { ...book, [event.target.name]: event.target.value };
    setBook(updatedBook);
  }

  function handleSubmit(event) {
    event.preventDefault();
    var changed = {};
    function populateChanged(now, old, title, temp) {
      if (now !== old) {
        temp[title] = now;
        return temp;
      } else {
        return temp;
      }
    }
    changed = populateChanged(
      book.name,
      defaultState.name,
      "Book_Name",
      changed
    );
    changed = populateChanged(
      book.author,
      defaultState.author,
      "Author",
      changed
    );
    changed = populateChanged(book.sno, defaultState.sno, "S_no", changed);
    changed = populateChanged(
      book.series,
      defaultState.series,
      "Series_Name",
      changed
    );
    changed = populateChanged(
      book.type,
      defaultState.type,
      "Fiction_Non_fiction_Companion_Prequel",
      changed
    );
    changed = populateChanged(book.genre, defaultState.genre, "Genre", changed);
    changed = populateChanged(
      book.kindleReal,
      defaultState.kindleReal,
      "Kindle_Real",
      changed
    );
    var temp_string = "";
    var key = "";
    var value = "";
    var temp_string_list = [];
    //debugger;
    for (var i = 0; i < Object.keys(changed).length; i++) {
      //debugger;
      key = Object.keys(changed)[i];
      value = changed[key];
      if (i !== Object.keys(changed).length - 1) {
        temp_string = `${key} = "${value}" AND `;
      } else if (i === Object.keys(changed).length - 1) {
        temp_string = `${key} = "${value}"`;
      }
      temp_string_list.push(temp_string);
      //debugger;
      temp_string = "";
      key = "";
      value = "";
    }

    var sql_t = temp_string_list.join("");
    var sql_tt = "SELECT * FROM books_catalouge WHERE ";
    var sql = sql_tt + sql_t;
    toast.success(sql);

    var request = new XMLHttpRequest();
    var jsql = JSON.stringify(sql);
    request.onreadystatechange = function() {
      //debugger;
      if (this.readyState == 4 && this.status == 200) {
        setAnswer([this.responseText, true]);
        console.log(`${answer}`);
      }
    };
    request.open(
      "GET",
      "http://localhost:3001/retrieve_books" + "?msg=" + jsql,
      true
    );
    request.send(jsql);
    console.log("This is the END");
    console.log(`${answer}`);
  }

  return (
    <>
      <Form book={book} onChange={handleChange} onSubmit={handleSubmit} />
      <br />
      <ResultsRenderer status={answer[1]} results={answer[0]} />
    </>
  );
}

export default Searcher;

如果您也需要 NodeJS,请告诉我。我正在使用 SQL 来获取数据,这就是我需要 NodeJS 的原因。对不起,如果我的代码有点奇怪。

提前致谢!

【问题讨论】:

  • 听起来好像第一次加载没有数据......console.log("I am ", results); 看看它是什么
  • @jdn...看代码
  • 请在第一行使用console.log(props.results),并将结果添加到问题中。
  • 您可能在父组件中使用&lt;Results results={this.state.x} /&gt;。解决此问题所需要做的就是确保this.state.x始终是一个数组,即以[]开头。
  • 尝试记录typeof results,我怀疑是字符串而不是数组

标签: javascript arrays reactjs object array.prototype.map


【解决方案1】:

函数map() 只能用于数组。在这种情况下,props.results 看起来不是数组或尚未设置(如果您使用 Axios 或类似的工具获取数据,可能会发生这种情况)。

我建议你在函数的开头放置这样的东西:

if (!props.results) return 'no data';
if (!Array.isArray(props.results)) return 'results are not array'

澄清后

您会收到对您的 onreadystatechange 请求的响应,该请求通常以 JSON 或 XML 格式出现。我认为你的答案是字符串化的 json。如果是 JSON,请尝试使用 JSON.parse(response),如果是 XML,请尝试使用 (new DOMParser()).parseFromString(response,"text/xml")

在您的组件中,它可能看起来像这样

request.onreadystatechange = function() {
   (this.readyState == 4 && this.status == 200)
      && setAnswer([JSON.parse(this.responseText), true]);
};

【讨论】:

  • 它返回,'结果不是数组'。
  • 所以...您的结果不是数组,函数map 仅适用于数组。你能用console.log() 转储它并发布已打印的内容吗?
  • 完成。出于某种原因,它看起来像一个数组。
  • 您确定在此组件/代码中引发了错误吗?我有tested your variable dumps,是的,它们是数组(使用了与我在回答中提到的相同的函数,所以如果值相同,它不会说它不是数组)。另一个可能的问题是,如果您正在使用一些 asyncPromise 函数(同样,它也可以是 Axios 或 Fetch)。你能告诉我这个父组件是从哪里渲染的吗?
  • 当然。给我一秒钟
【解决方案2】:

我在反序列化一个简单的 .json 文件时看到了类似的行为:

const stringifiedData = fs.readFileSync(animalsPath);
const animalData = JSON.parse(stringifiedData);
const animals = animalData.map(animal => {
    return new Animal(animal)
})

奇怪的是,我下面的例子是做一个字符串点表示法,它似乎满足 V8 的对象是一个数组,即使它在 console.out 中的输出没有改变。以下确实有效,但我不知道为什么。有什么想法吗?

const stringifiedData = fs.readFileSync(animalsPath);
const animalData = JSON.parse(stringifiedData).animals;
const animals = animalData.map(animal => {
    return new Animal(animal)
})  

【讨论】:

  • 帮助我,谢谢。损失了大约一个小时,因为我认为初始类型无关紧要(因为稍后将其替换为内容完整的数组)。我有这个: const [newReply, setNewReply] = useState("");我将其更改为: const [newReply, setNewReply] = useState([]);和宾果游戏。
【解决方案3】:

我在访问数组的数据元素时也遇到了同样的错误。这是我所做的:

{standardObj ? (
    {standardObj.map((obj: any) => {
      return (
        <Grid item>
          <FormControlLabel
            className={styles.CheckboxLabel}
            key={obj.Code}
            control={
              <Checkbox
                onChange={handleCheckElement}
                name={obj.FullName}
                value={obj.Code}
              />
            }
            label={obj.FullName}
          />
        </Grid>
      );
    })}
) : null }

【讨论】:

    【解决方案4】:

    我遇到了同样的问题,并且发现对于 useState Hook 来说初始值的数据类型非常重要,我的初始值是 0 int,而反应的 cos 没有将更新识别为数组。

    【讨论】:

      【解决方案5】:

      哪里有

       results.map(result => {
       ........................
       }
      

      只是做

      results.map(result => (
       ........................
       )
      

      【讨论】:

      • 您的答案可以通过额外的支持信息得到改进。请edit 添加更多详细信息,例如引用或文档,以便其他人可以确认您的答案是正确的。你可以找到更多关于如何写好答案的信息in the help center
      猜你喜欢
      • 1970-01-01
      • 2020-08-07
      • 2019-09-21
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2019-07-31
      • 2021-11-02
      • 2019-10-28
      相关资源
      最近更新 更多