webentwicklung-frage-antwort-db.com.de

React-Native FlatList-Leistungsprobleme mit großer Liste

Mein Code ruft Json-Daten in ein Array auf und listet die Daten mit einer FlatList auf. Es sieht aus wie ein Telefonbuchfoto und Text in einer Reihe.

Hier ist mein Code:

  renderItem = ({ item }) => 
    (
    <ListItem
      title={item.username}
      avatar={{ uri: item.photo }}
    />
    )


  render() {
    console.log(this.state.myData);
    return (
      <View style={styles.container}>
        <FlatList
          data={this.state.myData}
          renderItem={this.renderItem}
        />
      </View>
    );
  }

Es funktioniert und ich bekomme die Ausgabe, aber die Leistung ist langsam. Das Rendern dauert ungefähr 10 Sekunden, was für den Benutzer ärgerlich ist. Was soll ich tun, um es schneller zu machen?

5
bucsy

Hier einige Verbesserungen, die Sie zur Optimierung Ihrer Wohnungsliste vornehmen können:

  1. Seitennummerierung
    • Sie können Ihre Daten in Ihrem Backend paginieren und erneut abrufen, wenn sich Ihre Bildlaufrolle dem Ende nähert. onEndReached und onEndReachedThreshold können Ihnen helfen.
  2. Aktualisieren Sie Ihre React Native-Version auf 49 oder die neueste Version .
    • Fiber 16 bietet eine erstaunliche Leistungsverbesserung, wodurch alles schneller und reibungsloser läuft
  3. Verwenden Sie PureComponent für das Renderelement
    • PureComponent verbessert das Rendering und die Speicherauslastung Ihrer Komponente, da das Erstellen von Render-Elementen als reine Darstellung für eine bessere Leistung sorgt
  4. getItemLayout prop definieren
    • Es verbessert das Rendering von Elementen, da React seine Layoutdefinition zuvor kennt

Ich hoffe es hilft

2
soutot

Diese Antwort wurde zu einem größerer und vollständigerer Beitrag auf github


Wenn Sie diesem Thread folgen, werden Sie feststellen, dass das Team von reag bereits über dieses Leistungsproblem informiert ist.

Für dieses Thema gibt es keine silberne Kugel, Sie müssen die Abwägungen jedes Ansatzes in Betracht ziehen und Ihrer Meinung nach eine gute Erfahrung für Ihr Publikum. Glücklicherweise gibt es mehrere Optimierungen, mit denen Sie versuchen können, Ihre FlatList zu verbessern.


Begriffe und Bedeutungen

Es gibt viele Begriffe (zu docs oder zu einigen Problemen), die für mich zunächst verwirrend waren. Also, lassen Sie uns das von Anfang an aus dem Weg schaffen.

  • VirtualizedList ist die Komponente hinter FlatList und ist die Implementierung des Konzepts ' virtuelle Liste ' von React Native.

  • Performance impliziert in diesem Zusammenhang ein reibungsloses (nicht abgehacktes) Scrollen (und Navigieren in oder aus Ihrer Liste).

  • Speicherverbrauch gibt in diesem Zusammenhang an, wie viele Informationen zu Ihrer Liste im Speicher abgelegt werden, was zu einem Absturz der App führen kann.
  • Leere Bereiche bedeutet, dass die VirtualizedList Ihre Elemente nicht schnell genug rendern konnte, sodass Sie einen Teil Ihrer Liste mit nicht gerenderten Komponenten eingeben.
  • Window Hier ist nicht Ihr Ansichtsfenster, sondern die Größe des Bereichs, in dem Elemente gerendert werden sollen.

Requisiten

Eine Möglichkeit, Ihre FlatList zu verbessern, besteht darin, ihre Requisiten zu optimieren. Hier sind eine Liste von Requisiten, die Ihnen dabei helfen können.

removeClippedSubviews

Sie können die removeClippedSubviews-Eigenschaft auf true setzen, um Komponenten aufzuheben, die sich außerhalb des Fensters befinden.

Win: Dies ist sehr speicherfreundlich, da Sie immer eine kleine gerenderte Liste haben.

Kompromisse: Beachten Sie, dass diese Implementierung Fehler enthalten kann, z. B. fehlende Inhalte, wenn Sie sie für eine Komponente verwenden, die nicht abgehängt wird (z. B. eine Navigationsroute). Dies kann auch Seien Sie weniger performant und haben abgehackte Scroll-Animationen für große Listen mit komplexen Elementen auf nicht so guten Geräten, da sie verrückte Berechnungen pro Scroll durchführen.

maxToRenderPerBatch

Sie können den maxToRenderPerBatch={number} einstellen, der eine VirtualizedList-Eigenschaft ist, die direkt an FlatList übergeben werden kann. Hiermit können Sie die Anzahl der pro Stapel gerenderten Elemente steuern. Dies ist der nächste Block von Elementen, die bei jedem Bildlauf gerendert werden.

Win: Das Einstellen einer größeren Zahl bedeutet weniger sichtbare leere Bereiche beim Scrollen (besser die Füllrate).

Kompromisse: Mehr Artikel pro Stapel bedeuten weniger JavaScript-Leistung, was weniger Reaktionsfähigkeit bedeutet (Klicken auf ein Element und Öffnen des Details). Wenn Sie über eine statische und nicht interaktive Liste verfügen, könnte dies der Weg sein.

initialNumToRender

Sie können den initialNumToRender={number} einstellen. Dies bedeutet die anfängliche Menge der Elemente, die gerendert werden sollen.

Win: Sie können diesen Wert auf die genaue Anzahl der Elemente einstellen, die für jedes Gerät den Bildschirm abdecken würden. Dies kann einen großen Leistungsschub beim Rendern der Listenkomponente bedeuten.

Kompromisse: Bei der Einstellung eines niedrigen Werts initialNumToRender sehen Sie am wahrscheinlichsten leere Bereiche.

fenstergröße

Sie können den windowSize={number} einstellen. Die übergebene Anzahl ist eine Maßeinheit, wobei 1 Ihrer Ansichtsfensterhöhe entspricht. Der Standardwert ist 21, dh 10 Ansichtsfenster darüber, 10 darunter und eines dazwischen.

Win: Wenn Sie sich vor allem um die Leistung sorgen, können Sie ein größeres windowSize setzen, damit Ihre Liste reibungslos und mit weniger Leerzeichen ausgeführt wird. Wenn Sie sich vor allem um den Speicherverbrauch sorgen, können Sie eine niedrigere windowSize-Einstellung vornehmen, sodass Ihre gerenderte Liste kleiner wird.

Kompromisse: Für eine größere windowSize haben Sie einen größeren Speicherbedarf. Bei einer geringeren windowSize haben Sie eine geringere Leistung und größere Änderungen, wenn Sie leere Bereiche sehen.

legacyImplementation

Diese Requisite Wenn dies wahr ist, muss Ihr FlatList auf das ältere ListView anstelle von VirtualizedList angewiesen sein.

Win: Dadurch wird Ihre Liste definitiv besser, da Virtualisierung entfernt und alle Elemente gleichzeitig gerendert werden.

Kompromisse: Ihr Speicherverbrauch geht auf das Dach und die Chancen stehen gut, dass eine große Liste (100+) mit komplexen Elementen Ihre App zum Absturz bringt. Außerdem wird eine Warnung ausgegeben, dass die oben genannten Einstellungen abnehmen funktioniert nicht, weil Sie sich jetzt auf einer ListView befinden.

disableVirtualization

Sie werden Leute sehen, die die Verwendung dieser Stütze in einigen Fragen befürworten. Aber das ist jetzt veraltet . Dies tat etwas Ähnliches wie legacyImplementation.


Artikel auflisten

Es gibt auch einige Win-Win-Strategien, die Ihre Listenelementkomponenten umfassen. Sie werden häufig von VirtualizedList verwaltet und müssen daher schnell sein.

Verwenden Sie einfache Komponenten

Je komplexer Ihre Komponenten sind, desto langsamer werden sie gerendert. Versuchen Sie, viel Logik und Verschachtelung in Ihren Listenelementen zu vermeiden. Wenn Sie diese Listenelementkomponente häufig in Ihrer App wiederverwenden, erstellen Sie ein Duplikat nur für Ihre großen Listen und erstellen Sie sie mit weniger Logik als möglich und weniger verschachtelt als möglich.

Verwenden Sie leichte Komponenten

Je schwerer Ihre Komponenten sind, desto langsamer werden sie gerendert. Vermeiden Sie schwere Bilder (verwenden Sie eine abgeschnittene Version für Listenelemente, so klein wie möglich). Sprechen Sie mit Ihrem Designteam, verwenden Sie so wenig Effekte und Interaktionen und Informationen wie möglich in Ihrer Liste. Speichern Sie sie zu den Details Ihres Artikels.

Verwenden Sie shouldComponentUpdate

Implementieren Sie die Aktualisierungsüberprüfung für Ihre Komponenten. PureComponent von React eignet sich hauptsächlich für den Fall, dass Sie keine Zeit zum Nachdenken haben. Wenn Sie dies lesen, haben Sie Zeit, erstellen Sie also die strengsten Regeln für Ihre Listenelementkomponenten. Wenn Ihre Liste einfach genug ist, können Sie sogar verwenden

shouldComponentUpdate() {
  return false
}
12
Filipe Merker