Wann ist es wichtig, props
an super()
zu übergeben, und warum?
class MyComponent extends React.Component {
constructor(props) {
super(); // or super(props) ?
}
}
Es gibt nur einen Grund, warum man props
an super()
übergeben muss:
Wenn Sie im Konstruktor auf this.props
Zugreifen möchten.
Vorbeigehen:
class MyComponent extends React.Component {
constructor(props) {
super(props)
console.log(this.props)
// -> { icon: 'home', … }
}
}
Nicht bestanden:
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', … }
}
}
Beachten Sie, dass die Weitergabe von props
an super
keine Auswirkung auf spätere Verwendungen von this.props
Hat. außerhalb constructor
. Das heißt, render
, shouldComponentUpdate
oder Event-Handler haben immer Zugriff darauf.
Dies wird ausdrücklich in einer Sophie Alperts Antwort zu einer ähnlichen Frage gesagt.
Die Dokumentation — Status und Lebenszyklus, Hinzufügen eines lokalen Status zu einer Klasse, Punkt 2 - empfiehlt:
Klassenkomponenten sollten den Basiskonstruktor immer mit
props
aufrufen.
Es wird jedoch kein Grund angegeben. Wir können spekulieren, dass dies entweder auf eine Unterklasse oder auf zukünftige Kompatibilität zurückzuführen ist.
(Danke @MattBrowne für den Link)
In diesem Beispiel erweitern Sie die Klasse React.Component
. Gemäß der ES2015-Spezifikation kann ein untergeordneter Klassenkonstruktor this
erst verwenden, wenn super()
aufgerufen wurde. ES2015-Klassenkonstruktoren müssen auch super()
aufrufen, wenn sie Unterklassen sind.
class MyComponent extends React.Component {
constructor() {
console.log(this); // Reference Error
}
render() {
return <div>Hello {this.props.name}</div>;
}
}
Im Gegensatz:
class MyComponent extends React.Component {
constructor() {
super();
console.log(this); // this logged to console
}
render() {
return <div>Hello {this.props.name}</div>;
}
}
Mehr Details als diese hervorragende Stapelüberlaufantwort
Möglicherweise sehen Sie Beispiele für Komponenten, die durch Erweitern der Klasse React.Component
erstellt wurden und die super()
nicht aufrufen. Sie werden jedoch feststellen, dass diese Komponenten keine constructor
haben. Daher ist dies nicht erforderlich.
class MyOtherComponent extends React.Component {
render() {
return <div>Hi {this.props.name}</div>;
}
}
Ein Punkt der Verwirrung, den ich von einigen Entwicklern, mit denen ich gesprochen habe, gesehen habe, ist, dass die Komponenten, die keine constructor
haben und daher super()
nicht überall aufrufen, this.props
weiterhin in der render()
-Methode verfügbar sind. Denken Sie daran, dass diese Regel und die Notwendigkeit, eine this
-Bindung für die constructor
zu erstellen, nur für die constructor
gilt.
Wenn Sie props
an super
übergeben, werden die Requisiten this
zugewiesen. Sehen Sie sich folgendes Szenario an:
constructor(props) {
super();
console.log(this.props) //undefined
}
Wie auch immer, wenn Sie das tun:
constructor(props) {
super(props);
console.log(this.props) //props will get logged.
}
Wie pro Quellcode
function ReactComponent(props, context) {
this.props = props;
this.context = context;
}
sie müssen props
jedes Mal übergeben, wenn Sie Requisiten haben, und Sie müssen sie nicht manuell in this.props
einfügen.
Dan Abramov schrieb einen Artikel zu diesem Thema:
Warum schreiben wir super (Requisiten)?
Und das Wesentliche ist, dass es hilfreich ist, die Gewohnheit zu haben, vorüberzugehen um dieses Szenario zu vermeiden, das ich ehrlich gesagt nicht für unwahrscheinlich halte:
// 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
}
// ...
}
super()
wird verwendet, um den übergeordneten Konstruktor aufzurufen.
super(props)
würde props
an den übergeordneten Konstruktor übergeben.
In Ihrem Beispiel würde super(props)
den React.Component
-Konstruktor aufrufen, der props
als Argument übergeben würde.
Weitere Informationen zu super
: https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Operators/super
Hier ist die Geige, die ich gemacht habe: https://jsfiddle.net/beshanoe/zpxbLw4j/1/ . Es zeigt, dass Requisiten standardmäßig nicht im Konstruktor zugewiesen werden. Soweit ich weiß, werden sie in die Methode React.createElement
aufgenommen. Daher sollte super(props)
nur aufgerufen werden, wenn der Konstruktor der Superklasse manuell props
in this.props
eingibt. Wenn Sie nur die Erweiterung React.Component
erweitern, wird der Aufruf von super(props)
nichts mit Requisiten tun. Vielleicht wird es in den nächsten Versionen von React geändert.
Bei der Implementierung der constructor()
-Funktion in einer React-Komponente ist super()
eine Voraussetzung. Beachten Sie, dass Ihre MyComponent
-Komponente die Funktionalität der React.Component
-Basisklasse erweitert oder entlehnt.
Diese Basisklasse verfügt über eine constructor()
-Funktion mit etwas Code, um unsere React-Komponente für uns einzurichten.
Wenn wir eine constructor()
-Funktion in unserer MyComponent
-Klasse definieren, überschreiben oder ersetzen wir im Wesentlichen die constructor()
-Funktion, die sich in der React.Component
-Klasse befindet. Wir müssen jedoch sicherstellen, dass der gesamte Setup-Code in dieser constructor()
-Funktion weiterhin aufgerufen wird.
Um sicherzustellen, dass die constructor()
-Funktion von React.Component
aufgerufen wird, rufen wir super(props)
auf. super(props)
ist ein Verweis auf die Elternfunktion constructor()
, das ist alles, was es ist.
Wir müssen super(props)
jedes Mal hinzufügen, wenn wir eine constructor()
-Funktion in einer klassenbasierten Komponente definieren.
Andernfalls wird ein Fehler angezeigt, der besagt, dass wir super(props)
aufrufen müssen.
Der gesamte Grund für die Definition dieser constructor()
-Funktion besteht darin, unser Zustandsobjekt zu initialisieren.
Um unser Zustandsobjekt zu initialisieren, schreibe ich unterhalb des Super-Aufrufs:
class App extends React.Component {
constructor(props) {
super(props);
this.state = {};
}
// React says we have to define render()
render() {
return <div>Hello world</div>;
}
};
Wir haben also unsere constructor()
-Methode definiert, unser Statusobjekt initialisiert, indem wir ein JavaScript-Objekt erstellt haben, ihm eine Eigenschaft oder ein Schlüssel/Wert-Paar zuweisen und das Ergebnis davon this.state
zuweisen. Natürlich ist dies hier nur ein Beispiel, daher habe ich dem Statusobjekt nicht wirklich ein Schlüssel/Wert-Paar zugewiesen, es ist nur ein leeres Objekt.
Hier bekommen wir das nicht im Konstruktor, also gibt es undefined zurück, aber wir können es außerhalb der Konstruktorfunktion abrufen
class MyComponent extends React.Component {
constructor() {
console.log(this); // Reference Error i.e return undefined
}
render() {
return <div>Hello {this.props.name}</div>;
}
}
Wenn wir super () verwenden, können wir die "this" -Variable auch im Konstruktor abrufen
class MyComponent extends React.Component {
constructor() {
super();
console.log(this); // this logged to console
}
render() {
return <div>Hello {this.props.name}</div>;
}
}
Also wenn wir super () verwenden; wir können dies abrufen, aber this.props wird im Konstruktor undefiniert sein. Anders als Konstruktor wird this.props nicht undefiniert zurückgeben.
Wenn wir super (Requisiten) verwenden, können wir auch diesen this.props-Wert im Konstruktor verwenden.
Wenn Sie this.props im Konstruktor verwenden möchten, müssen Sie .__ übergeben. Requisiten zu super. Andernfalls spielt es keine Rolle, weil React .props .__ setzt. auf der Instanz von außen unmittelbar nach dem Aufruf von Konstrukteur.
Für die reale Version 16.6.3 verwenden wir super (props), um das Statuselementname zu initialisieren: this.props.name
constructor(props){
super(props);
}
state = {
name:this.props.name
//otherwise not defined
};