React: Fragen zu "props.children"

Erstellt am 26. Mai 2018  ·  6Kommentare  ·  Quelle: facebook/react

Möchten Sie eine Funktion anfordern oder einen Fehler melden?
Nur Fragen

Einige Fragen zu props.children

In der offiziellen React-Dokumentation von React.Children können Sie lesen, dass this.props.children eine "undurchsichtige Datenstruktur" ist.
Was bedeutet das GENAU?

Ich denke, es gibt im Allgemeinen drei Möglichkeiten für die Transparenz der Datenstruktur von props.children :

Fall 1: JEDER Aspekt der Datenstruktur props.children ist offen und gut definiert.

Wenn dies richtig wäre, wäre der Begriff "undurchsichtige Datenstruktur" völlig falsch.
Daher ist "Fall 1" offensichtlich nicht der Fall.

Fall 2: KEIN Aspekt der props.children -Datenstruktur ist offen oder klar.

Das würde bedeuten, dass Sie, wenn Sie props.children es IMMER in Kombination mit React.Children MÜSSEN, da React.Children die einzige ist (mmmh, ist es wirklich die einzige?). Wer kennt die tatsächliche Datenstruktur von props.children .

Dies würde jedoch bedeuten, dass es weder verwendet werden darf

javascript // This is used almost everywhere (even in the official React documentation) <div>{this.props.children}</div>

Noch

javascript // This is often seen with the "Function as child" pattern MyComponent.propTypes = { children: PropTypes.func.isRequired, };

Da beide Beispiele sehr häufig sind, scheint "Fall 2" offensichtlich auch nicht der Fall zu sein.

Fall 3: Einige Aspekte der props.children -Datenstruktur sind offen und gut definiert.

Dies würde die Möglichkeit eröffnen, dass eines oder sogar beide Beispiele in "Fall 2" gültig sind.
Aber dann würde es bedeuten, dass es eine genaue Spezifikation geben sollte, welche Aspekte von props.children gut und offen definiert sind und welche Aspekte wirklich undurchsichtig sind.
Vielleicht habe ich etwas in der React-Dokumentation verpasst, aber ich denke, es ist dort nicht wirklich genau spezifiziert, oder?

Und zu guter Letzt noch eine Frage:

Warum genau ist props.children für den Fall, dass es einige Kinder gibt (ein oder mehrere), nur immer ein Array (wie es zum Beispiel in "Preact" gemacht wird)? Das würde die Dinge so viel einfacher machen, nicht wahr?

Vielen Dank im Voraus für die Klarstellungen.

Question

Hilfreichster Kommentar

_Opaque-Datenstruktur_ bezieht sich auf die Tatsache, dass children eine Menge Dinge sein kann: Arrays, Fragmente, einzelne Elemente, String-Literale usw.

_React.Children_ enthält einige Methoden, mit denen Sie auf einheitliche Weise mit den verschiedenen Arten von children _ arbeiten können. Dies ist definitiv nicht die einzige Möglichkeit, mit ihnen zu interagieren.

Warum genau ist props.children nicht für den Fall, dass es einige Kinder gibt (ein oder mehrere), nur immer ein Array (wie es zum Beispiel in "Preact" gemacht wird)?

Abgesehen von der Tatsache, dass es in JSX eine Abkürzung gibt, ist children eine Eigenschaft wie jede andere. In der Tat können Sie es angeben als:

<Component children={...}/>

Wenn React das DOM aktualisieren muss, ist es viel teurer festzustellen, ob zwei Arrays mit einem Element identisch sind, als ob zwei primitive Werte (z. B. Zeichenfolgen) identisch sind.

Abgesehen davon denke ich, dass die React.Children-Dokumentation möglicherweise etwas erweitert wurde, aber das ist ein Problem, das im Repository von

Dieser Artikel kann die Dinge ein wenig klären, das hat er für mich getan!

Alle 6 Kommentare

_Opaque-Datenstruktur_ bezieht sich auf die Tatsache, dass children eine Menge Dinge sein kann: Arrays, Fragmente, einzelne Elemente, String-Literale usw.

_React.Children_ enthält einige Methoden, mit denen Sie auf einheitliche Weise mit den verschiedenen Arten von children _ arbeiten können. Dies ist definitiv nicht die einzige Möglichkeit, mit ihnen zu interagieren.

Warum genau ist props.children nicht für den Fall, dass es einige Kinder gibt (ein oder mehrere), nur immer ein Array (wie es zum Beispiel in "Preact" gemacht wird)?

Abgesehen von der Tatsache, dass es in JSX eine Abkürzung gibt, ist children eine Eigenschaft wie jede andere. In der Tat können Sie es angeben als:

<Component children={...}/>

Wenn React das DOM aktualisieren muss, ist es viel teurer festzustellen, ob zwei Arrays mit einem Element identisch sind, als ob zwei primitive Werte (z. B. Zeichenfolgen) identisch sind.

Abgesehen davon denke ich, dass die React.Children-Dokumentation möglicherweise etwas erweitert wurde, aber das ist ein Problem, das im Repository von

Dieser Artikel kann die Dinge ein wenig klären, das hat er für mich getan!

Vielen Dank an @danburzo für Ihre Antworten und
Nach Ihrer Antwort ist klar, dass ich das Wort "undurchsichtig" dort gerade völlig falsch verstanden habe.
In der React-Dokumentation wollte nur gesagt werden, dass die Datenstruktur von props.children ein vollständig genau definierter Unionstyp ist und sich in ihrer konkreten Darstellung unterscheidet (wie es Unionstypen immer tun).

Ich habe gerade eine ältere Ausgabe gefunden, die genau das gleiche Thema behandelte - frage mich, was mit diesen Änderungen passiert ist?!? (Ich habe ein Problem unter reactjs.org => reactjs / reactjs.org # 914 geöffnet):

https://github.com/facebook/react/pull/6018/files/91223423410f107ff83a8a6ce3158c488247292f?short_path=ef51787#diff -ef51787305cfed62f6f564284762d4de

Trotzdem möchte ich noch einmal die zweite Frage stellen:
Warum ist "props.children" KEIN Array für den Fall, dass es genau EIN Kind gibt (es scheint wirklich ein Verstoß gegen das Prinzip des geringsten Erstaunens zu sein, wenn Sie den Hintergrund nicht kennen => wenn der Name "Kinder" oder "Gegenstände" ist oder "Token" erwarten Sie normalerweise eine Sammlung)?
Ist es wirklich aus Leistungsgründen? Ich kann nicht wirklich sehen, dass die Berechnung von "checkResult" unten so zeitaufwändig ist:

const
  child1 = ...,
  child2 = ...,
  child1IsArray = Array.isArray(child1),
  child2IsArray = Array.isArray(child2),

  checkResult = child1IsArray && child2IsArray
     && child1.length === 1 && child2.length === 1
     && child1[0] === child2[0]; 

Tut mir leid, wenn ein erneutes Fragen etwas nervig erscheint - aber ich würde wirklich gerne den genauen Grund für diese Designentscheidung wissen ...

Ich bin froh, dass ich Ihnen beim ersten Teil Ihrer Frage helfen konnte! Leider habe ich keine genaue Antwort darauf, warum einzelne Kinder nicht als Array mit einem einzelnen Element dargestellt werden. Ich wollte jedoch darauf hinweisen, dass Sie ein einzelnes Kind immer noch als normale Requisite (anstelle der JSX-Kurzform) gültig übergeben können, was ich versehentlich mit meiner Hypothese verdunkelt habe, dass es mit der Leistung zusammenhängt.

@danburzo Nochmals vielen Dank für Ihre Antwort.

Mmh, ehrlich gesagt hoffte ich, dass sich vielleicht jemand aus dem React-Team an den eigentlichen Grund für diese Designentscheidung erinnern würde ...
Weil es wirklich einige subtile Probleme mit dem Umgang mit Requisiten für Kinder in React gibt.
Fragen Sie beispielsweise einen React-Neuling, ob sich die Komponenten Test1 und Test2 im folgenden Beispiel gleich verhalten (Sie als React-Profi wissen, dass die Antwort "Nein" lautet => Test2 warnt DEV vor den fehlenden Schlüsseln, während Test1 dies tut nicht - aber ist das wirklich das, was du erwarten würdest, wenn du ein Neuling wärst?!?)

const
  h = React.createElement,
  Test1 = () => h('div', null, h('br'), h('br')),
  Test2 = () => h('div', { children: [h('br'), h('br')] });

ReactDOM.render(
  h('div', null, h(Test1), h(Test2)),
  document.getElementById('container')
);

Übrigens: Wenn Test2 erlaubt wäre, hätte dies einige subtile Leistungsvorteile, wenn Sie einige createElement -Ersetzungen ersetzen - wie zum Beispiel eine Hyperscript-Funktion.

Ein weiteres Beispiel: Fragen Sie einen React-Neuling, wie "Kinder: PropTypes ..." aussehen würde, wenn alle Kinder eine bestimmte Bedingung erfüllen müssen. Ich denke, das wäre nicht einfach zu beantworten (zumindest für einen Neuling).

An das React-Team: Wenn die Gründe für die betreffende Designentscheidung nicht wirklich bekannt sind oder nur Geschmackssache waren, können Sie dieses Problem natürlich gerne schließen.

Ich gehe davon aus, dass die Entscheidung, kein Array für ein einzelnes Kind zu verwenden, getroffen wurde, um unnötige Array-Zuweisungen zu vermeiden.

Weil es wirklich einige subtile Probleme mit dem Umgang mit Requisiten für Kinder in React gibt.

Wir empfehlen im Allgemeinen nicht, eine explizite children Requisite zu verwenden. Die meisten Benutzer verwenden auch JSX, anstatt React.createElement direkt aufzurufen, sodass die von Ihnen erwähnten Probleme normalerweise kein Problem darstellen.

@aweary Danke für deine Antwort

War diese Seite hilfreich?
0 / 5 - 0 Bewertungen