JavaScript >> Javascript-Tutorial >  >> Tags >> map

WeakMap in JavaScript – eine einfache Einführung

WeakMap ist eine der am meisten unterschätzten und am wenigsten verwendeten Datenstrukturen in JavaScript. Es gibt viele JavaScript-Entwickler, die nicht einmal wissen, dass sie existieren. Dieses Tutorial hilft Ihnen, sie zu verstehen. Sie erfahren, was WeakMaps sind, wie sie funktionieren und wie sie sich von Maps unterscheiden.

Eine kurze Einführung in WeakMap

Sowohl Maps als auch WeakMaps sind neue Datenstrukturen oder Sammlungen, die in [ES6] eingeführt wurden. Ein weiteres Beispiel für eine Sammlung ist ein Array. Ähnlich wie bei einem Array können Sie sowohl mit Maps als auch mit WeakMaps Daten speichern. Im Falle dieser Maps und WeakMaps speichern Sie in Form von Schlüssel-Wert-Paaren.

Wenn Sie auf einen in einer Karte gespeicherten Wert zugreifen möchten, brauchen Sie nur den richtigen key zu verwenden . Dies funktioniert auch für WeakMaps. Wenn Sie auf einen Wert zugreifen möchten, der in einer WeakMap gespeichert ist, müssen Sie auch den korrekten key verwenden . Sowohl mit Maps als auch mit WeakMaps können Sie neue Schlüsselwertpaare hinzufügen und vorhandene entfernen.

Was ist, wenn Sie sich nicht sicher sind, ob eine Map oder WeakMap einen bestimmten Schlüssel enthält? Es gibt eine Methode, mit der Sie schnell überprüfen können, ob der Schlüssel vorhanden ist. Hier funktionieren Maps und WeakMaps also auf die gleiche Weise. Neben diesen Ähnlichkeiten gibt es einige wichtige Unterschiede zwischen diesen beiden, die Sie kennen sollten.

Unterschiede zwischen Maps und WeakMaps

Der erste Unterschied zwischen Maps und WeakMaps ist die Art der Daten, die Sie verwenden können. Mit Maps können Sie jeden beliebigen Datentyp verwenden, um einen Schlüssel für das Schlüssel-Wert-Paar zu erstellen. Dazu gehören auch Objekte und Funktionen. Dies gilt nicht für WeakMaps. Mit WeakMaps können Sie Schlüssel nur mit Objekten erstellen, nicht mit anderen Datentypen.

Dies ist einer der Hauptunterschiede zwischen Maps und WeakMaps. Ein weiterer wichtiger Unterschied besteht darin, dass alle Schlüssel in einer WeakMap schwach referenziert sind. Das bedeutet, dass Objekte, die als Schlüssel für eine WeakMap verwendet werden, weiterhin von der Garbage Collection erfasst werden können. Dies geschieht, wenn alle Verweise auf diese Objekte verschwunden sind.

Wenn diese Objekte von keinem Teil des Programms mehr verwendet werden, befreit die Garbage Collection sie aus dem Speicher. Es ist wichtig zu beachten, dass die Garbage Collection diese Objekte nicht sofort aus dem Speicher befreit. Diese Objekte werden nur für die Garbage Collection „markiert“.

Erst wenn der nächste „Zyklus“ des gesammelten Mülls stattfindet, werden sie tatsächlich befreit. JavaScript führt diese Zyklen automatisch aus. Sie müssen sich also keine Sorgen machen. Der letzte große Unterschied zwischen Maps und WeakMaps besteht darin, dass WeakMaps nicht iterierbar sind. Sie können sie nicht mit einer Schleife oder forEach() durchlaufen Methode wie über Maps.

Das bedeutet auch, dass Sie den gesuchten Schlüssel kennen müssen. Da wir über Iterabilität sprechen. WeakMaps haben auch keine size Eigentum. Sie wissen also nicht wirklich, wie viele Paare sich in einem befinden. Schließlich gibt es kein clear() Methode, die es ermöglichen würde, alle Daten aus einer WeakMap zu entfernen.

Diese Unterschiede sind ziemlich wichtig und schränken die Möglichkeiten von WeakMaps stark ein. Lassen Sie sich davon jedoch nicht davon abhalten, mehr über sie zu erfahren, da WeakMaps immer noch nützlich sein können. Wir werden bald darüber sprechen, aber lassen Sie uns zuerst einen Blick darauf werfen, wie Sie WeakMaps erstellen und was Sie damit machen können.

So erstellen Sie WeakMaps

Wenn Sie eine WeakMap erstellen möchten, müssen Sie den WeakMap()-Konstruktor verwenden. Dieser Konstruktor erstellt ein neues WeakMap-Objekt. Wenn Sie dieses Objekt haben, können Sie alles tun, was Sie wollen. Sie können neue Schlüssel-Wert-Paare hinzufügen, vorhandene überprüfen, abrufen oder entfernen.

// Create new WeakMap
const myWeakMap = new WeakMap()

WeakMap-Methoden

Standardmäßig bieten WeakMaps eine Reihe von Methoden, die die Arbeit mit ihnen erleichtern. Mit diesen Methoden können Sie (fast) alles tun, was Sie tun möchten. Diese Methoden sind set() , get() , delete() und has() . Werfen wir einen kurzen Blick auf die einzelnen.

Elemente hinzufügen

Wenn Sie WeakMaps ein neues Schlüssel-Wert-Paar hinzufügen möchten, den set() Methode ist, was Sie brauchen. Diese Methode benötigt zwei Parameter. Der erste Parameter ist für key innerhalb des Schlüssel-Wert-Paares. Dies wird ein Objekt sein. Der zweite Parameter ist für value . Dies kann ein String, eine Zahl, ein boolescher Wert usw. sein.

Eines müssen Sie bei set() beachten Methode. Mit dieser Methode können Sie jeweils nur ein Schlüssel/Wert-Paar hinzufügen. Wenn Sie mehrere Paare hinzufügen möchten, müssen Sie diese Methode mehrmals anwenden, einmal für jedes Paar.

// Create new WeakMap
const myWeakMap = new WeakMap()

// Create some objects
const myObj1 = { name: 'Dexter' }
const myObj2 = { name: 'Jordan' }
const myObj3 = {}

// Add three new key-value pairs
myWeakMap.set(myObj1, 'I am not quite sure about this guy.')
myWeakMap.set(myObj2, 'This is a baller.')
myWeakMap.set(myObj3, 'We fired this guy a month ago.')


// You can also chain set() methods
myWeakMap
  .set(myObj1, 'This is first object.')
  .set(myObj2, 'This is second object.')
  .set(myObj3, 'This is third object.')

Werte abrufen

Die get() -Methode ist das, wonach Sie suchen, wenn Sie Werte von WeakMaps abrufen möchten. Diese Methode nimmt einen Parameter, das Objekt, das Sie als Schlüssel für den abzurufenden Wert verwendet haben. Wenn der Schlüssel vorhanden ist, get() -Methode gibt den ihr zugeordneten Wert zurück. Andernfalls wird undefined zurückgegeben .

// Create new WeakMap
const myWeakMap = new WeakMap()

// Create some objects
const myObj1 = { language: 'JavaScript' }
const myObj2 = { language: 'Python' }
const myObj3 = { language: 'Rust' }

// Add two new key-value pairs
myWeakMap.set(myObj1, 'Language for every platform, soon even a fridge.')
myWeakMap.set(myObj2, 'I kind of miss those curly braces.')

// Retrieve the value associated with "myObj1"
myWeakMap.get(myObj1)
// Output:
// 'Language for every platform, soon even a fridge.'

// Try to retrieve the value associated with "myObj3"
// that was not added to "myWeakMap"
myWeakMap.get(myObj3)
// Output:
// undefined

// Try to retrieve the value associated with non-existing "myObj3"
myWeakMap.get(myObj4)
// Output:
// ReferenceError: myObj3 is not defined

Elemente entfernen

Der beste und wahrscheinlich einzige Weg, Elemente aus WeakMaps zu entfernen, ist mit delete() Methode. Diese Methode benötigt einen Parameter, einen Schlüssel. Dies ist das Objekt, das Sie als Schlüssel zum Speichern des damit verbundenen Werts verwendet haben. Diese Methode gibt entweder true zurück oder false . true wenn das Paar im WeakMap-Objekt erfolgreich entfernt wurde.

Wenn das Paar nicht entfernt wurde, wird false zurückgegeben . Sie erhalten auch false wenn der Schlüssel nicht in der WeakMap existiert. Dasselbe passiert auch, wenn das Objekt, das Sie als Schlüssel übergeben möchten, eigentlich kein Objekt ist.

// Create new WeakMap
const myWeakMap = new WeakMap()

// Create some objects
const myObj1 = { language: 'JavaScript' }
const myObj2 = { language: 'Python' }
const myObj3 = {}

// Add two new key-value pairs
myWeakMap.set(myObj1, 'Semicolons or not?')
myWeakMap.set(myObj2, 'White space matters.')

// Remove the value associated with "myObj2"
myWeakMap.delete(myObj2)
// Output:
// true

// Try to remove the value associated with "myObj2" again
myWeakMap.delete(myObj2)
// Output:
// false

// Try to use "myObj3" that is not in myWeakMap
myWeakMap.delete(myObj2)
// Output:
// false

Nach vorhandenen Schlüsseln suchen

Sie wissen, wie Sie Werte hinzufügen, abrufen und entfernen. Das Letzte, was Sie tun können, ist zu prüfen, ob ein Schlüssel in einer WeakMap vorhanden ist. Sie können dies mit dem has() tun Methode. Diese Methode nimmt einen Parameter, irgendein Objekt, das Sie wissen möchten, wenn es als key verwendet wird . Wenn der key existiert der has() -Methode gibt true zurück . Andernfalls false .

// Create new WeakMap
const myWeakMap = new WeakMap()

// Create some objects
const myObj1 = { language: 'PHP' }
const myObj2 = { language: 'Pearl' }

// Check if "myObj1" is used as a key in "myWeakMap"
myWeakMap.set(myObj1, 'Not that dead yet.')
// Output:
// true

// Check if "myObj1" is used as a key in "myWeakMap"
myWeakMap.has(myObj1)
// Output:
// true

// Check if "myObj2" is used as a key in "myWeakMap"
myWeakMap.has(myObj2)
// Output:
// false

Mögliche Anwendungsfälle für WeakMaps

WeakMaps mögen auf den ersten Blick nicht als etwas Nützliches erscheinen, vielleicht auch auf den zweiten. Das bedeutet jedoch nicht, dass sie nutzlos sind. Es ist wahr, dass sie nicht die beste Wahl sind, wenn Sie einige Daten speichern möchten. Andere Sammlungen wie Arrays, Objekte, Maps oder Sets erledigen die Arbeit viel besser.

Ein Szenario, in dem WeakMaps sehr gut funktioniert, ist, wenn Sie Objekten einige zusätzliche Werte hinzufügen möchten. Wenn Sie dies mit Maps versuchen, verhindern Sie, dass diese Objekte von der Garbage Collection erfasst werden. Dies kann zu schlechterer Leistung und Speicherlecks führen. Dies ist bei WeakMaps kein Problem, da sie die Garbage-Collection nicht verhindern.

Wenn Sie ein Objekt zu einer WeakMap hinzufügen und später alle Verweise auf dieses Objekt entfernen, wird es von der Garbage Collection erfasst. Es gibt auch einen weiteren potenziellen Vorteil der Verwendung von WeakMaps in diesem und ähnlichen Szenarien. WeakMaps sind im Grunde Black Boxes. Sie können sie nicht durchlaufen, um die Elemente zu erhalten, die sie enthalten. Sie können auch nicht ihre Größe abrufen.

Das bedeutet, dass Sie wissen müssen, welches Objekt Sie als Schlüssel verwenden müssen, um einen bestimmten Wert zu erhalten. Andernfalls werden Sie es nicht bekommen. Eine andere erwähnenswerte Sache ist das Fehlen jeglicher Clearing-Methode. Sie können nicht alle Elemente auf einmal aus WeakMap entfernen. Sie können sie nur einzeln entfernen und nur, wenn Sie wissen, welchen Schlüssel Sie verwenden müssen.

Aus dieser Sicht kann WeakMaps Ihnen mehr Sicherheit bieten, als andere Sammlungen oder Datenstrukturen. Dieser Sicherheitsvorteil geht sogar noch weiter, wenn Sie die Garbage Collection berücksichtigen. Entfernen Sie alle Verweise auf ein Objekt und alle „sensiblen“ Daten, die diesem Objekt zugeordnet sind, werden früher oder später ebenfalls gelöscht.

Fazit:WeakMap in JavaScript – Ein einfacher Einstieg

WeakMaps sind eine dieser weniger bekannten Funktionen von JavaScript. Es ist wahr, dass sie nicht die beste Wahl für die Speicherung von Daten sind. Es gibt jedoch Jobs, für die WeakMaps besser geeignet ist. Beispielsweise das Hinzufügen einiger zusätzlicher Metadaten zu Objekten. WeakMaps kann das ganz gut.

Ich hoffe, dass dieses Tutorial Ihnen geholfen hat zu verstehen, was WeakMaps sind, wie sie funktionieren, wie sie sich von Maps und anderen Sammlungen unterscheiden und wie sie verwendet werden.