无法读取 React.js 中未定义的属性“setState”
Cannot read property ‘setState’ of undefined in React.js
当在没有将正确的上下文绑定到关键字的情况下调用类方法时,会发生“无法读取未定义的属性‘setState’”错误this
。
要解决该错误,请将类方法定义为箭头函数或使用
bind
类的构造方法中的方法。
壳
Uncaught TypeError: Cannot read properties of undefined (reading 'setState')
下面是错误如何发生的示例。
应用程序.js
import React, {Component} from 'react'; class App extends Component { constructor(props) { super(props); this.state = { isActive: false, }; } toggleIsActive() { // ⛔️ `this` is undefined here // Uncaught TypeError: Cannot read properties of undefined (reading 'setState') this.setState({isActive: !this.state.isActive}); } render() { console.log(this.state.isActive); return ( <div> <button onClick={this.toggleIsActive}>Toggle</button> </div> ); } } export default App;
请注意,我们定义了toggleIsActive
方法,但没有绑定this
关键字的上下文。
因此,方法
this
中的关键字toggleIsActive
的值为undefined
。要解决该错误,请将toggleIsActive
方法切换为使用箭头函数。
索引.js
import React, {Component} from 'react'; class App extends Component { constructor(props) { super(props); this.state = { isActive: false, }; } // ✅ Works because we used an arrow function // to declare the method toggleIsActive = () => { this.setState({isActive: !this.state.isActive}); }; render() { console.log(this.state.isActive); return ( <div> <button onClick={this.toggleIsActive}>Toggle</button> </div> ); } } export default App;
这是可行的,因为箭头函数使用this
封闭范围的关键字——在我们的示例中,封闭范围是特定的组件实例。
或者,您可以
在类的构造函数中调用Function.bind()方法。
应用程序.js
import React, {Component} from 'react'; class App extends Component { constructor(props) { super(props); this.state = { isActive: false, }; // ✅ Bind method here this.toggleIsActive = this.toggleIsActive.bind(this); } // ✅ Works toggleIsActive() { // ✅ `this` is correctly bound here this.setState({isActive: !this.state.isActive}); } render() { console.log(this.state.isActive); return ( <div> <button onClick={this.toggleIsActive}>Toggle</button> </div> ); } } export default App;
该bind
方法创建并返回一个新函数,其中this
关键字设置为提供的值。
构造函数中的关键字this
引用类实例。
在 vanilla JavaScript 类中工作时也是如此。
索引.js
class Person { constructor(first, last) { this.first = first; this.last = last; console.log(this); // 👉️ {first: 'James', last: 'Doe'} } } const p1 = new Person('James', 'Doe');
这使我们能够绑定 中的方法constructor
并在整个类中使用绑定版本。
我的首选方法是尽可能使用箭头函数来定义我的类方法。这样我就不必考虑关键字this
,默认情况下一切正常。