React.js:无法在render()函数

时间:2017-07-17 16:50:04

标签: javascript node.js reactjs

如何在render函数中获取对象数组的属性。如果我试试这个:

render() {
    console.log(this.state.items[0].name);
 (...)

我收到了一个错误:

  

TypeError:this.state.items [0]未定义

  class App extends React.Component {
  constructor() {
    super()

    this.state = {
      items: []
    }
  }
  componentWillMount() {
    fetch('http://swapi.co/api/people/?format=json')
      .then((response) => response.json())
        .then(({ results: items }) => this.setState({ items }))
  }

  filter(e){
    this.setState({ filter: e.target.value })
    console.log(this.state.items[0].name);
  }

  render() {
    console.log(this.state.items[0].name);
    return (
      <div>
        <input type="text" onChange={this.filter.bind(this)}  />
      </div>
    )
  }

}
export default App

但是,如果我只注销数组的第一个元素

 console.log(this.state.items[0])

打印出对象

  

对象{名称:“Luke Skywalker”,身高:“172”,质量:“77”,hair_color:“金色”,skin_color:“fair”,eye_color:“blue”,birth_year:“19BBY”,性别: “男性”,家乡:“http://swapi.co/api/planets/1/”,电影:数组[5],还有6个......}

当过滤函数被触发时,我得到了第一个元素的属性     的console.log(this.state.items [0]。名称)

打印出来:

  

Luke Skywalker

这里发生了什么?

2 个答案:

答案 0 :(得分:2)

在您的提取完成之前,您的state.items数组未设置。您的渲染方法将在此之前调用,因此,它不会按预期工作。

如果您重新检查控制台输出,我会感觉您在对象显示之前会看到一些空值或未定义。

试试这个:

 render() {
    console.log(this.state.items.length > 0 ? this.state.items[0].name : 'Items not loaded yet');
    return (
      <div>
        <input type="text" onChange={this.filter.bind(this)}  />
      </div>
    )
  }

答案 1 :(得分:1)

fetch是异步调用,因此在第一次呈现时会this.state.items []并且您正在尝试访问不存在的第0项name ,因此而抛出错误。

使用时:

console.log(this.state.items);

检查控制台是否正在打印两个值[],另一个将是您从服务器获取的数据。

<强>解决方案:

检查内部渲染的长度,一旦得到响应,它将打印正确的名称。

像这样:

render(){
   if(this.state.items.length)
       console.log(this.state.items[0].name);

   return(
       ....
   )
}