Detaillierte Erklärung des JS-Speicherplatzes

Detaillierte Erklärung des JS-Speicherplatzes

Überblick

Variable Objekte und Heap-Speicher

var a = 20;
var b = "abc";
var c = wahr;
var d = { m: 20 } 

Lange Zeit dachte ich, dass das Konzept des Speicherplatzes beim Erlernen von JS nicht so wichtig sei. Als ich mich jedoch später noch einmal mit den Grundlagen von JS befasste, stellte ich fest, dass ich aufgrund meiner vagen Vorstellungen davon viele Dinge nicht verstand. Was sind beispielsweise die grundlegendsten Referenzdatentypen und Referenzübergabemethoden? Was ist beispielsweise der Unterschied zwischen einer flachen Kopie und einer tiefen Kopie? Es gibt auch Verschlüsse, Prototypen und so weiter.

Daher wurde mir allmählich klar, dass ich ein klares Verständnis des Speicherplatzes haben muss, wenn ich ein tieferes Verständnis von JS erlangen möchte.

1. Stapeln und Aufhäufen

Hinweis: Stapel kann auch Stapel genannt werden

Im Gegensatz zu C/C++ unterscheidet JavaScript nicht strikt zwischen Stapelspeicher und Heap-Speicher. Daher können wir grob davon ausgehen, dass alle JavaScript-Daten im Heap-Speicher gespeichert sind. In einigen Szenarien müssen wir jedoch immer noch auf der Idee der Stapeldatenstruktur basieren, z. B. dem Ausführungskontext von JavaScript (ich werde den Ausführungskontext im nächsten Artikel zusammenfassen). Der Ausführungskontext implementiert den Stapel logisch. Daher ist es nach wie vor sehr wichtig, die Prinzipien und Eigenschaften der Stapeldatenstruktur zu verstehen.

Um einfach zu verstehen, wie auf den Stapel zugegriffen wird, können wir ihn anhand einer Analogie zu einer Ping-Pong-Box analysieren. Wie auf der linken Seite des Bildes unten gezeigt.

Ping-Pong-Box und Stapel-Analogie

Die Art und Weise, wie die Ping-Pong-Bälle gespeichert werden, ist exakt die gleiche wie die Art und Weise, wie Daten im Stapel gespeichert und abgerufen werden. Der Ping-Pong-Ball 5 in der obersten Lage der Schachtel muss als letztes eingelegt werden, kann aber als erster verwendet werden. Wenn wir den Ping-Pong-Ball 1 unten verwenden möchten, müssen wir die vier Ping-Pong-Bälle oben herausnehmen, sodass Ping-Pong-Ball 1 in der obersten Schicht der Schachtel liegt. Dies sind die First-In-Last-Out- und Last-In-First-Out-Eigenschaften des Stapelspeichers. Die Abbildung hat das Speicherprinzip des Stapelspeichers detailliert dargestellt.

Die Art und Weise, wie ein Heap Daten speichert und darauf zugreift, ähnelt stark der eines Bücherregals und von Büchern.

Obwohl die Bücher ordentlich im Bücherregal verstaut sind, können wir, solange wir den Namen des Buches kennen, leicht das gewünschte Buch herausnehmen, anstatt alle Ping-Pong-Bälle aus der Schachtel zu nehmen, um einen Ping-Pong-Ball in der Mitte zu finden. Beispielsweise können in JSON-formatierten Daten die von uns gespeicherten Schlüssel-Wert-Paare ungeordnet sein, da die unterschiedliche Reihenfolge unsere Verwendung nicht beeinflusst. Wir müssen uns nur um den Namen des Buches kümmern.

2. Variable Objekte und grundlegende Datentypen

Nachdem der JavaScript-Ausführungskontext generiert wurde, wird ein spezielles Objekt namens Variablenobjekt erstellt (die Details werden zusammen mit dem Ausführungskontext im nächsten Artikel zusammengefasst). Die grundlegenden Datentypen von JavaScript werden häufig im Variablenobjekt gespeichert.

Streng genommen werden variable Objekte auch im Heap-Speicher gespeichert. Aufgrund der speziellen Funktionen variabler Objekte müssen wir sie beim Verständnis jedoch immer noch vom Heap-Speicher unterscheiden.

Grundlegende Datentypen sind einfache Datensegmente. In JavaScript gibt es 5 grundlegende Datentypen, nämlich Undefined, Null, Boolean, Number und String. Auf grundlegende Datentypen wird über den Wert zugegriffen, da wir den in der Variablen gespeicherten tatsächlichen Wert direkt bearbeiten können.

3. Referenzdatentypen und Heap-Speicher

Im Gegensatz zu anderen Sprachen haben Referenzdatentypen von JS, beispielsweise Arrays, Werte von nicht festgelegter Größe. Der Wert eines Referenzdatentyps ist ein im Heap-Speicher gespeichertes Objekt. JavaScript erlaubt keinen direkten Zugriff auf Speicherorte im Heap-Speicher. Daher können wir den Heap-Speicherplatz eines Objekts nicht direkt manipulieren. Wenn Sie an einem Objekt arbeiten, arbeiten Sie eigentlich an der Objektreferenz und nicht am eigentlichen Objekt. Daher wird auf Werte von Referenztypen per Referenz zugegriffen. Die Referenz kann hier grob als eine im variablen Objekt gespeicherte Adresse verstanden werden, die dem tatsächlichen Wert des Heap-Speichers zugeordnet ist.

Um variable Objekte und Heap-Speicher besser zu verstehen, können wir sie anhand der folgenden Beispiele und Diagramme verstehen.

var a1 = 0; // variables Objekt var a2 = 'this is string'; // variables Objekt var a3 = null; // variables Objekt var b = { m: 20 }; // Variable b existiert im variablen Objekt, {m: 20} existiert als Objekt im Heap-Speicher var c = [1, 2, 3]; // Variable c existiert im variablen Objekt, [1, 2, 3] existiert als Objekt im Heap-Speicher 

Illustration des obigen Beispiels

Wenn wir daher auf den Referenzdatentyp im Heap-Speicher zugreifen möchten, erhalten wir zuerst die Adressreferenz (oder den Adresszeiger) des Objekts aus dem variablen Objekt und dann die benötigten Daten aus dem Heap-Speicher.

Nachdem wir den Speicherplatz von JS verstanden haben, können wir die Eigenschaften des Speicherplatzes verwenden, um einige Eigenschaften des Referenztyps zu überprüfen.

In Front-End-Interviews stoßen wir häufig auf eine ähnliche Frage.

// demo01.js
var a = 20;
var b = a;
b = 30;

// Was ist der Wert von a zu diesem Zeitpunkt?
// demo02.js
var m = { a: 10, b: 20 }
var n = m;
na = 15;

// Wie hoch ist der Wert von ma zu diesem Zeitpunkt

Wenn Daten in einem variablen Objekt kopiert werden, weist das System der neuen Variablen automatisch einen neuen Wert zu. Nachdem var b = a ausgeführt wurde, sind die Werte von a und b zwar beide gleich 20, aber tatsächlich unabhängig voneinander und beeinflussen sich nicht gegenseitig. Einzelheiten finden Sie im Bild. Nachdem wir den Wert von b geändert haben, ändert sich der Wert von a nicht.

demo01 Diagramm

In demo02 führen wir eine Operation zum Kopieren von Referenztypen durch, indem wir var n = m verwenden. Beim Kopieren eines Referenztyps wird der neuen Variable ebenfalls automatisch ein neuer Wert zugewiesen und im Variablenobjekt gespeichert, der Unterschied besteht jedoch darin, dass dieser neue Wert lediglich ein Adresszeiger des Referenztyps ist. Wenn die Adresszeiger gleich sind, ist das spezifische Objekt, auf das im variablen Objekt zugegriffen wird, tatsächlich dasselbe, obwohl sie unabhängig voneinander sind. Wie auf dem Bild zu sehen.

Wenn ich also n ändere, ändert sich auch m. Dies liegt in der Natur von Referenztypen.

demo02 Diagramm

Wenn Sie es aus der Perspektive der Erinnerung verstehen, wird es Ihnen viel leichter fallen. Darüber hinaus können wir dies auch als Grundlage verwenden, um wichtige Konzepte wie den Ausführungskontext, die Gültigkeitsbereichskette, den Abschluss, die Prototypenkette usw. von JavaScript Schritt für Schritt zu verstehen. Den Rest werde ich in zukünftigen Artikeln langsam zusammenfassen, also bleiben Sie dran.

Speicherplatzverwaltung

Da JavaScript über einen automatischen Speicherbereinigungsmechanismus verfügt, müssen wir uns während der Entwicklung keine Gedanken über die Speichernutzung machen. Die Speicherzuweisung und -wiederverwendung werden vollständig automatisch verwaltet. Aufgrund meiner eigenen Entwicklungserfahrung hilft mir das Verständnis des Speichermechanismus jedoch dabei, klar zu verstehen, was während der Ausführung des von mir geschriebenen Codes passiert ist, sodass ich Code mit besserer Leistung schreiben kann. Deshalb ist es sehr wichtig, auf das Gedächtnis zu achten.

JavaScript-Speicherlebenszyklus

1. Weisen Sie den benötigten Speicher zu

2. Den zugewiesenen Speicher verwenden (lesen, schreiben)

3. Geben Sie es frei oder geben Sie es zurück, wenn es nicht mehr benötigt wird

Zum besseren Verständnis erklären wir diesen Zyklus anhand eines einfachen Beispiels.

var a = 20; // Speicherplatz für eine numerische Variable reservieren alert(a + 100); // Speicher verwenden var a = null; // Speicherplatz nach Verwendung freigeben

Der erste und zweite Schritt sind leicht zu verstehen. JavaScript führt die Speicherzuweisung beim Definieren von Variablen durch. Beim dritten Schritt, dem Freigeben von Speicherplatz, müssen wir uns auf das Verständnis dieses Punktes konzentrieren.

JavaScript verfügt über einen automatischen Speicherbereinigungsmechanismus. Was ist also das Prinzip dieses automatischen Speicherbereinigungsmechanismus? Eigentlich ist es ganz einfach: Suchen Sie einfach die Werte, die nicht mehr verwendet werden, und geben Sie dann den Speicher frei, den sie belegen. Der Garbage Collector führt in regelmäßigen Abständen einen Freigabevorgang durch.

In JavaScript wird am häufigsten der Mark-and-Sweep-Algorithmus verwendet, um herauszufinden, welche Objekte nicht mehr verwendet werden. Daher gibt a = null tatsächlich nur die Referenz frei, wodurch der ursprünglich a entsprechende Wert die Referenz verliert und die Ausführungsumgebung verlässt. Dieser Wert wird gefunden und freigegeben, wenn der Garbage Collector das nächste Mal eine Operation ausführt. Und die Dereferenzierung zum richtigen Zeitpunkt ist ein wichtiger Weg, um die Leistung Ihrer Seite zu verbessern.

Im lokalen Bereich werden die lokalen Variablen bei der Ausführung der Funktion nicht mehr benötigt, sodass der Garbage Collector sie problemlos beurteilen und wiederverwenden kann. Es ist jedoch schwierig zu bestimmen, wann globale Variablen automatisch Speicherplatz freigeben müssen. Daher müssen wir bei unserer Entwicklung die Verwendung globaler Variablen so weit wie möglich vermeiden, um Leistungsprobleme zu vermeiden. Um mehr über den Garbage Collection-Mechanismus zu erfahren, wird empfohlen, Abschnitt 4.3 von „Advanced JavaScript Programming“ zu lesen.

Oben finden Sie eine ausführliche Erläuterung des JS-Speicherplatzes. Weitere Informationen zum JS-Speicherplatz finden Sie in den anderen verwandten Artikeln auf 123WORDPRESS.COM!

Das könnte Sie auch interessieren:
  • Detaillierte Erklärung des Speicherplatzes, der Zuweisung und der tiefen und flachen Kopien von JavaScript
  • Ein Artikel zum Verständnis von Javascript-Speicherlecks
  • Fehlerbehebung bei hohem Speicherverbrauch von NodeJs, tatsächlicher Kampfrekord
  • So schreiben Sie speichereffiziente Anwendungen mit Node.js
  • JavaScript-Garbage-Collection-Mechanismus und Speicherverwaltung
  • Analyse häufiger JS-Speicherlecks und Lösungen
  • Detaillierte Erläuterung des Beispiels eines Javascript-Speichermodells
  • Analyse mehrerer Beispiele für durch JS verursachte Speicherlecks
  • Detaillierte Erläuterung des JavaScript-Stapelspeichers und des Heapspeichers
  • So gehen Sie mit JavaScript-Speicherlecks um

<<:  Implementierungsmethode der rekursiven MySQL-Baumabfrage

>>:  Verwenden Sie nginx, um virtuelle Hosts auf Domänennamenbasis zu konfigurieren

Artikel empfehlen

Neue Verwendung von watch und watchEffect in Vue 3

Inhaltsverzeichnis 1. Neue Verwendung der Uhr 1.1...

Schritte zum Übertragen des neuen Kernels auf das Linux-System

1. Laden Sie das Ubuntu16.04-Image und den entspr...

MySQL Server IO 100 % Analyse- und Optimierungslösung

Vorwort Während des Stresstests besteht das unmit...

Vue implementiert ein verschiebbares Baumstrukturdiagramm

Inhaltsverzeichnis Rekursive Vue-Komponente Drag-...

Lösung für falsche Zeichenfolgenwerte in MySQL

Viele Freunde berichten von folgendem Fehler, wen...

Vergleich zwischen Redis und Memcache und Auswahlmöglichkeiten

Ich verwende Redis seit Kurzem und finde es recht...

Ein Artikel, der Ihnen HTML beibringt

Wenn Sie nicht unbedingt Künstler werden möchten,...

Verwenden Sie vue2+elementui für Hover-Prompts

Die Hover-Prompts von Vue2+elementui sind in exte...