什么时候把props传递给super()很重要,为什么?
props
super()
class MyComponent extends React.Component { constructor(props) { super(); // or super(props) ? } }
根据源代码
function ReactComponent(props, context) { this.props = props; this.context = context; }
你必须通过props每次你有道具,你不把他们放入this.props手动。
this.props
这是我做的小提琴:jsfiddle.net。它表明默认情况下道具不是在构造函数中分配的。据我所知,它们被分配在方法React.createElement中。因此,只有当父类的构造函数手动将props赋值给this.props时,才应该调用super(props)。如果你只是扩展了React.Component,那么调用super(props)对道具没有任何作用。也许它会在React的下一个版本中被改变。
React.createElement
super(props)
React.Component
super()用于调用父构造函数。
super(props)将把props传递给父构造函数。
在您的示例中,super(props)将调用React.Component构造函数,并传入props作为参数。
super
在这个例子中,你正在扩展React.Component类,根据ES2015规范,子类构造函数在调用super()之前不能使用this;此外,如果ES2015类是子类,它们的构造函数必须调用super()。
this
class MyComponent extends React.Component { constructor() { console.log(this); // Reference Error } render() { return <div>Hello {this.props.name}</div>; } }
相比之下:
class MyComponent extends React.Component { constructor() { super(); console.log(this); // this logged to console } render() { return <div>Hello {this.props.name}</div>; } }
更多细节见这个很棒的堆栈溢出答案
您可能会看到通过扩展React.Component类创建的不调用super()的组件的示例,但您会注意到这些组件没有constructor,因此它是不必要的。
constructor
class MyOtherComponent extends React.Component { render() { return <div>Hi {this.props.name}</div>; } }
我从与我交谈过的一些开发人员那里看到的一个困惑是,组件没有constructor,因此在任何地方都不调用super(),但在render()方法中仍然有this.props可用。记住,这个规则和这个需要为constructor创建一个this绑定,只适用于constructor。
render()
只有一个原因需要将props传递给super():
当你想在构造函数中访问this.props时。
传递:
class MyComponent extends React.Component { constructor(props) { super(props) console.log(this.props) // -> { icon: 'home', … } } }
不通过:
class MyComponent extends React.Component { constructor(props) { super() console.log(this.props) // -> undefined // Props parameter is still available console.log(props) // -> { icon: 'home', … } } render() { // No difference outside constructor console.log(this.props) // -> { icon: 'home', … } } }
请注意,将props传递或不传递给super会在constructor之外的this.props后面使用没有影响。这是render, shouldComponentUpdate或事件处理程序总是可以访问它。
render
shouldComponentUpdate
Sophie Alpert在回答中明确地回答了一个类似的问题。
文档——# EYZ0-recommends:
类组件应该始终使用props调用基构造函数。
但是,没有提供理由。我们可以推测,这要么是因为子类化,要么是为了未来的兼容性。
(感谢@MattBrowne提供的链接)
当你传递props到super时,道具被分配给this。看看下面的场景:
constructor(props) { super(); console.log(this.props) //undefined }
当你这样做的时候:
constructor(props) { super(props); console.log(this.props) //props will get logged. }
当在React组件中实现constructor()函数时,super()是一个要求。请记住,您的MyComponent组件是从React.Component基类扩展或借用功能的。
constructor()
MyComponent
这个基类有一个自己的constructor()函数,里面有一些代码,用来为我们设置React组件。
当我们在MyComponent类中定义constructor()函数时,我们实际上覆盖或替换了React.Component类中的constructor()函数,但我们仍然需要确保这个constructor()函数中的所有设置代码仍然被调用。
因此,为了确保React.Component的constructor()函数被调用,我们调用super(props)。super(props)是父函数constructor()的引用,仅此而已。
每次在基于类的组件中定义constructor()函数时,我们都必须添加super(props)。
如果我们不这样做,我们将看到一个错误,说我们必须调用super(props)。
定义这个constructor()函数的全部原因是初始化我们的状态对象。
所以为了初始化我们的state对象,在super调用下面我将写:
class App extends React.Component { constructor(props) { super(props); this.state = {}; } // React says we have to define render() render() { return <div>Hello world</div>; } };
因此,我们已经定义了constructor()方法,通过创建JavaScript对象初始化状态对象,为其分配属性或键/值对,并将结果分配给this.state。当然这只是一个例子,所以我并没有给state对象分配一个键/值对,它只是一个空对象。
this.state
这里我们不会在构造函数中获取这个,所以它将返回undefined,但是我们可以在构造函数外获取这个
class MyComponent extends React.Component { constructor() { console.log(this); // Reference Error i.e return undefined } render() { return <div>Hello {this.props.name}</div>; } }
如果我们使用super(),那么我们也可以在构造函数中获取“this”变量
当我们使用super();我们可以得到这个,但是这个。Props在构造函数中没有定义。除了构造函数,还有这个。Props不会返回undefined。
如果我们使用super(道具),那么我们可以使用这个。Props在构造函数中的值
Sophie Alpert的回答 .
如果你想使用这个。构造函数中的道具,需要传递 为超级喝彩。否则,没关系,因为React会设置.props 调用后立即从外部调用实例 构造函数。< / p >
对于react版本16.6.3,我们使用超级(道具)初始化状态元素name: this.props.name .name
constructor(props){ super(props); } state = { name:this.props.name //otherwise not defined };
Dan Abramov写了一篇关于这个话题的文章:
< a href = " https://overreacted。io/ Why - Do - We - Write -super-props/" rel="noreferrer">为什么我们要写super(props)?< / >
它的要点是,它有助于养成通过的习惯,以避免这种情况,老实说,我不认为它不太可能发生:
// Inside React class Component { constructor(props) { this.props = props; // ... } } // Inside your code class Button extends React.Component { constructor(props) { super(); // 😬 We forgot to pass props console.log(props); // ✅ {} console.log(this.props); // 😬 undefined } // ... }