【问题标题】:How to use setState in map function如何在地图函数中使用 setState
【发布时间】:2020-01-10 08:04:16
【问题描述】:

我正在尝试在地图功能中使用 setState 当我点击改变状态的点击按钮时我想要做什么

我在stackoverflow中搜索了“In map function changed setState”

但很难理解..并应用我的案例

this.state = {
      categories: [
        {
          category: 'sports',
          ariticles: [],
          isClick: true
        },

...
...

 return (
      <div>
        <hr></hr>

        <div className="categoryBtn">
          {this.state.map(item => (
            <button
              onClick={
                () => this.setState(() => (item.isClick = false))
                // () => console.log((item.isClick = false))
                // this.setState(() => (item.isClick = !item.isClick))
              }
            >
              {' '}
              {item.category}
            </button>
          ))}

当我点击按钮时,我收到错误“this.state.map 不是函数”

我希望当我点击按钮时,isClick 会被切换

【问题讨论】:

  • .map 仅在可迭代中可用,您的 this.state 是一个对象,我认为您需要引用 categories 数组。所以应该是this.state.categories.map(...

标签: javascript reactjs


【解决方案1】:

您的this.state 指的是一个包含数组的对象,

categories: [...]

所以你需要映射 this.state.categories.map 而不是 this.state.map


另外,我注意到button 事件处理程序会改变状态。

<button onClick={() => this.setState(() => (item.isClick = false))}>
  {item.category}
</button>

您需要返回一个新项目 reference 以通知 react 状态已更改,并添加一个 key 属性。

谢天谢地,有人问了使用key的原因(仅2小时前)并回复了,您可以参考一下。

https://stackoverflow.com/a/57838612/4035

<button key={item.category} onClick={() => this.setState({
    find the item by searching for each item in `this.state.cateogies`
  })}>
  {item.category}
</button>;

但是找到合适的元素变得很困难,所以我建议标准化(意思是改变this.state.categories)看起来像下面这样更容易设置状态。

// From this
this.state = {
  categories: [
    {
      category: "sports",
      ariticles: [],
      isClick: true
    },
    {
      category: "sports",
      ariticles: [],
      isClick: true
    }
  ]
};

// to this
this.state = {
  categories: {
    sports: {
      category: 'sports',
      ariticles: [],
      isClick: true
    },
    news: {
      category: 'news',
      ariticles: [],
      isClick: true
    }
  }
};

这样,你可以设置如下状态。

<button
  key={item.category}
  onClick={() =>
    this.setState({
      [item.category]: {
        isClick: false
      }
    })
  }
>
  {item.category}
</button>

回复comment below(我已经为非韩语人士翻译了评论)

所以你做了这样的改变之后就不能再使用.map了?

对不起,我应该在状态更新后更新类别项生成代码。

不,您不能使用.map,因为它现在是一个对象。但幸运的是,您可以使用Object.keys/value/entries 来迭代this.state.categories

您可以点击“Run code sn-p”按钮查看输出

let state = {
  categories: {
    sports: {
      category: "sports",
      ariticles: [],
      isClick: true
    },
    news: {
      category: "news",
      ariticles: [],
      isClick: true
    }
  }
};

Object.entries(state.categories).map(([id, item]) => console.log(item))

所以你的代码看起来像,

<div className="categoryBtn">
  {Object.entries(state.categories).map(([id, item]) => (
    <button
      key={id}
      onClick={() =>
        this.setState({
          [item.category]: {
            isClick: false
          }
        })
      }
    >
      {item.category}
    </button>
  ))}
</div>

【讨论】:

  • 친절한 답변 감사드립니다 @Sung M. Kim
  • 근데 위와 같이 바꾼다면 map을 쓸 수 없는거 아닌가요..?@Sung M. Kim
  • @youngban this.state.categories는 이제 object이라서 map은 못쓰시구요, Object.entries/value/keys를 사용 하시면 됩니다。 제 위에있는 대답을 참고 해주세요.
  • 감사합니다! 다시해보겠습니다 @Sung M. Kim
【解决方案2】:

试试这个 :::

{this.state.categories.map(item => ( ..... ))}

【讨论】:

  • 与已经存在的答案相比没有什么新的。没有努力提供一些解释为什么代码不起作用,而这个应该。
  • 我相信我的打字速度比他快一点。但是由于@Mariselvam 是新的贡献者,感谢您回复答案。下次您可以尝试提供更彻底的答案,这是我为 {...?} 的 +1 ?
猜你喜欢
  • 1970-01-01
  • 2020-02-10
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2020-03-19
  • 2020-04-13
相关资源
最近更新 更多