English | 简体中文 | 繁體中文 | Русский язык | Français | Español | Português | Deutsch | 日本語 | 한국어 | Italiano | بالعربية

A brief discussion on references and copies in JavaScript (pass by value and pass by reference)

Es scheint, dass niemand sehr oft über die Referenzen und Kopien in JavaScript spricht, aber das Verständnis dieser Konzepte kann viel helfen

Lassen Sie uns zunächst über einige grundlegende Dinge sprechen, um zu sehen, welche Werte verschiedene Datentypen in JavaScript übertragen

Referenz: Objekt, Array, Funktion

Kopie: Nummer, Boolean

Der String ist besonders zu erwähnen, da seine Besonderheit es nicht zulässt, zu bestimmen, ob es sich um einen Wert oder eine Referenz handelt (da der Wert eines Strings nicht geändert werden kann, ist es auch bedeutungslos, darüber nachzudenken), aber offensichtlich gehört er zu den Wertvergleichsoperationen (darauf werde ich später eingehen)

Nächste, wie sich das im Gebrauch konkret zeigt

Der häufigste Gebrauch ist die Zuweisung

var a = 1;
var b = a;  //Hier wird eine Kopie des Wertes von a zugewiesen
b ++;
alert(a);  //"1"Die Änderungen an b haben keinen Einfluss auf a
/****************************************/
var a = [1};
var b = a;   //Hier wird eine Referenz von a zugewiesen 
b[0] ++;
alert(a); //"2"Die Änderungen an b wirken auch auf a, aber natürlich b = [2]; Diese Änderung ist für a nutzlos.

Funktion参数

Wertübergabe: Der übergebene Wert ist eine Kopie der Zahl, die Änderungen an ihr in der Funktion sind extern unsichtbar

var a = 1;
var b = 2;
function change(a,b) {
 var c = a;
 a = b;   //Neue Referenzen ersetzen
 b = c;
 alert(a);  //"2"     
 alert(b);  //"1"
};
change(a,b);
alert(a);  //"1"     
alert(b);  //"2"

Adressübergabe:Wertübergabe: Der übergebene Wert ist eine Referenz auf eine Zahl, die Änderungen an den Attributen in der Funktion sind extern sichtbar, aber durch neue Referenzen ersetzt, sind sie extern unsichtbar, zum Beispiel

var a = [1, 2, 3};
var b = [5, 6};
function change(a,b) {
 a[0] = 4;  //Die Änderungen an den Attributen sind extern sichtbar 
 var c = a;
 a = b;   //Neue Referenzen ersetzen
 b = c;
 alert(a);  //"5,6"     
 alert(b);  //"4,2,3"
};
change(a,b);
alert(a);  //"4,2,3"
alert(b);   //"5,6"

Wie das Ergebnis zeigt, haben a und b nicht gewechselt, weil die neue Referenz außen sichtbar ist. Das ist sehr natürlich, weil die Funktion nur die Referenz erhalten hat und das Recht nicht hat, die Referenz zu ändern

Das ist anders

var a = [1, 2, 3};
var b = [5, 6};
function change() {
 var c = a;
 a[0] = 4;
 a = b;
 b = c;
};
change();
alert(a);  //"5,6"
alert(b);  //"4,2,3"

Hier wurde der Austausch erfolgreich durchgeführt 

Noch einmal die Blockklauseln in JS zu erwähnen. In einigen anderen Sprachen würde dies sicherlich einen Fehler wegen nicht definiertem Fehler geben, weil JS keine Blockklauseln hat. Daher sucht es in change nach den Variablen a, b und findet sie nicht, und geht dann von selbst auf die höhere Ebene, daher sind hier a, b Referenzen globaler Variablen

Und die obigen Variablen a, b sind Variablen der Funktion change. Beim Aufruf der Funktion werden die Referenzen von a, b an diese Variablen übertragen, aber sie können nicht die globalen Variablen a, b ändern. Es hilft, wenn man sie in andere Namen um benennt...

Das ist nur eine kurze Erwähnung... etwas vom Thema abgekommen...

Zurück zum Vergleich von Referenzen und Kopie: Hinweise bei der Verwendung von Vergleichsoperationen

Der Vergleich von Werten ist der Vergleich von Zahlen, während der Vergleich von Referenzen die Referenzen vergleicht. Selbst wenn die Werte gleich sind, sind Referenzen unterschiedlich nicht gleich.

1 == 1;  //true
1 === 1;  //true
[0] == [0]; //false
[0][0] == [0][0];  //true
[0][0] === [0][0];  //true
[0].toString() == [0].toString();  //true 

In Klammerungen...

Klammerungen sind wahrscheinlich die am meisten verwirrende Sache in JS. Das klassische Interview-Beispiel in unserer Abteilung, das immer wieder verwendet wird...

Hier sage ich erst einmal nichts über Klammerungen, sondern nur über den Teil, der mit dem Übertragen von Werten und Referenzen zu tun hat. Wenn ich eines Tages sicher sein kann, dass ich diese Sache klar und prägnant mit lebhaften Beispielen erklären kann, werde ich diese wichtige Angelegenheit, die man nicht in der JS-Ausgabe erwähnen kann, detailliert erläutern...

In Klammerungen verwenden die inneren Funktionen die lokalen Variablen der äußeren Funktion auf dem Weg der Referenz, nicht auf dem Weg der Kopie.

Tatsächlich ist dies auch ein sehr wichtiger Teil des Verständnisses von Klammerungen. Man kann damit ein sehr klassisches Phänomen der Klammerungen erklären, das oft bei der Erklärung von Klammerungen verwendet wird.

/*Erstellen Sie eine Funktion, um dem Array von Knoten Ereignishandler zuzuweisen. Wenn Sie auf einen Knoten klicken, wird die Nummer des Knotens mit alert angezeigt.*/
var add_handlers = function(nodes) {
  var i;
  for (i = 0, l = nodes.length; i < l; i ++) {
    nodes[i].onclick = function(e) {
      alert(i);  // Natürlich ist das Ergebnis hier zwangsläufig, dass bei jedem alert immer die Knotenzahl angezeigt wird ...
    };
  };
};

Warum wird bei jedem alert immer die Knotenzahl angezeigt und nicht die erwartete Nummer, das ist sehr einfach zu erklären, wenn man sich auf Kopie und Referenz bezieht

Weil die interne Funktion die externen Variablen durch Referenz verwendet, d.h. wenn ich jedem Knoten das onclick-Ereignis setze, gebe ich die Referenz von i an alert weiter. Wenn ich den Knoten betätige, der das onclick-Ereignis auslöst, hat der Wert von i sich bereits auf die Anzahl der Knoten erhöht ...

var add_handlers = function(nodes) {
  var i;
  for (i = 0, l = nodes.length; i < l; i ++) {
    nodes[i].onclick = function(i) {
      return function() {
      alert(i);  
      };
 }(i);
  };
};

Der Grund, warum dies nach der Änderung korrekt ist, liegt darin, dass hier die Kopie des Wertes von i übergeben wird, was im Grunde genommen gleich einem gewöhnlichen Funktion ist. Man sollte sich nicht verwirren lassen, weil man eine Kapsel hinzugefügt hat, und zurück zu den Ursprüngen denken, um zu verstehen, dass der Ursprung das ist, was ich oben als Referenzübergabe erwähnt habe

Ich möchte noch hinzufügen, dass man sich nicht von dem seltsamen Namen 'Kapsel' abschrecken lassen sollte, tatsächlich ist es gleich dem Prinzip der Funktionen, die wir normalerweise verwenden. Abgesehen von den angeblichen Eigenschaften wie 'längerer Lebenszyklus' und 'Schutz privater Variablen' ist es einfach zu verstehen, wenn man es als gewöhnliche Funktion ansieht (oder man kann auch die globale Funktion als besondere Kapsel betrachten), was leicht verständlich ist

Der Schlüssel ist es, alle Prunk zu lassen und zur Essenz zurückzukehren ... und ich habe wieder vom Thema abgelenkt ...

Diese kurze Einführung in die Referenz und Kopie (Wert und Referenz) im JavaScript, die der Autor allen zur Verfügung gestellt hat, hofft, den Lesern eine Referenz zu bieten und hofft, dass alle mehr Unterstützung für die Anleitung rufen.

You may also like