JavaScript-Handbuch Teil 3: Variablen, Datentypen, Ausdrücke, Objekte

Im dritten Teil der Übersetzung des JavaScript-Handbuchs werden wir heute über verschiedene Möglichkeiten zum Deklarieren von Variablen, Datentypen, Ausdrücken und zum Arbeiten mit Objekten sprechen.

Teil 1: Erstes Programm, Sprachfunktionen, Standards
Teil 2: Codestil und Programmstruktur
Teil 3: Variablen, Datentypen, Ausdrücke, Objekte
Teil 4: Funktionen
Teil 5: Arrays und Loops
Teil 6: Ausnahmen, Semikolons, Platzhalterliterale
Teil 7: Strict Mode, dieses Schlüsselwort, Ereignisse, Module, mathematische Berechnungen
Teil 8: Übersicht über die ES6-Funktionen
Teil 9: Übersicht über die ES7-, ES8- und ES9-Standards



Variablen


Eine Variable ist eine Kennung, der ein Wert zugewiesen wird. Auf die Variable kann im Programm zugegriffen werden, wobei auf diese Weise mit dem ihr zugewiesenen Wert gearbeitet wird.

Eine Variable in JavaScript selbst enthält keine Informationen über den Wertetyp, der darin gespeichert wird. Dies bedeutet, dass Sie durch Schreiben in eine Variable, z. B. eine Zeichenfolge, später eine Zahl in diese schreiben können. Eine solche Operation verursacht keinen Fehler im Programm. Aus diesem Grund wird JavaScript manchmal als "untypisierte" Sprache bezeichnet.

Bevor eine Variable verwendet wird, muss sie mit dem Schlüsselwort var oder let deklariert werden. Wenn es um Konstanten geht, wird das Schlüsselwort const verwendet. Das Deklarieren einer Variablen und das Zuweisen eines bestimmten Werts ist ohne Verwendung dieser Schlüsselwörter möglich, dies wird jedoch nicht empfohlen.

▍ Schlüsselwort var


Vor dem ES2015-Standard war die Verwendung des Schlüsselworts var die einzige Möglichkeit, Variablen zu deklarieren.

 var a = 0 

Wenn var in diesem Konstrukt weggelassen wird, wird der Wert einer nicht deklarierten Variablen zugewiesen. Das Ergebnis dieser Operation hängt vom Modus ab, in dem das Programm ausgeführt wird.

Wenn also der sogenannte strikte Modus aktiviert ist, führt dies zu einem Fehler. Wenn der strikte Modus nicht aktiviert ist, wird eine implizite Variablendeklaration durchgeführt und dem globalen Objekt zugewiesen. Dies bedeutet insbesondere, dass eine Variable, die in einer bestimmten Funktion implizit auf diese Weise deklariert ist, auch dann verfügbar ist, wenn die Funktion ihre Arbeit abgeschlossen hat. Normalerweise wird erwartet, dass in Funktionen deklarierte Variablen ihre Grenzen nicht überschreiten. Es sieht so aus:

 function notVar() { bNotVar = 1 //    } notVar() console.log(bNotVar) 

Es wird 1 Konsole bNotVar = 1 , normalerweise erwartet niemand dieses Verhalten vom Programm. Der Ausdruck bNotVar = 1 sieht nicht wie ein Versuch aus, eine Variable zu deklarieren und zu initialisieren, sondern wie ein Versuch, auf eine Variable zuzugreifen, die sich in einem externen Bereich der Funktion befindet (dies ist ganz normal). Infolgedessen verwirrt die implizite Deklaration von Variablen denjenigen, der den Code liest, und kann zu unerwartetem Programmverhalten führen. Später werden wir über Funktionen und Bereiche sprechen. Versuchen Sie vorerst immer, spezielle Schlüsselwörter zu verwenden, wenn die Bedeutung eines Ausdrucks darin besteht, eine Variable zu deklarieren. Wenn in diesem Beispiel der Funktionskörper als var bNotVar = 1 umgeschrieben wird, führt der Versuch, das obige Codefragment zu starten, zu einer Fehlermeldung (die in der Browserkonsole angezeigt wird).

Es könnte beispielsweise so aussehen Uncaught ReferenceError: bNotVar is not defined . Seine Bedeutung beruht auf der Tatsache, dass das Programm nicht mit einer nicht vorhandenen Variablen arbeiten kann. Es ist viel besser, wenn Sie das Programm zum ersten Mal starten, eine solche Fehlermeldung zu sehen, als unverständlichen Code zu schreiben, der sich unerwartet verhalten kann.

Wenn beim Deklarieren einer Variablen diese nicht initialisiert wird und ihr kein Wert zugewiesen wird, wird ihr automatisch der undefined Wert zugewiesen.

 var a //typeof a === 'undefined' 

Mit dem Schlüsselwort var deklarierte Variablen können wiederholt deklariert werden, indem ihnen neue Werte zugewiesen werden (dies kann jedoch jemanden verwirren, der den Code liest).

 var a = 1 var a = 2 

Sie können mehrere Variablen in einem Ausdruck deklarieren:

 var a = 1, b = 2 

Der Bereich einer Variablen wird als Bereich des Programms bezeichnet, in dem auf diese Variable zugegriffen werden kann (sichtbar).

Eine Variable, die mit dem Schlüsselwort var außerhalb einer Funktion initialisiert wurde, wird einem globalen Objekt zugewiesen. Es hat einen globalen Geltungsbereich und ist von überall im Programm zugänglich. Wenn eine Variable mit dem Schlüsselwort var in einer Funktion deklariert wird, ist sie nur innerhalb dieser Funktion sichtbar und eine lokale Variable für sie.

Wenn eine Variable in einer Funktion mit var deklariert wird, deren Name mit dem Namen einer bestimmten Variablen aus dem globalen Bereich übereinstimmt, wird die globale Variable "überschrieben". Das heißt, wenn auf eine solche Variable innerhalb der Funktion zugegriffen wird, wird ihre lokale Version verwendet.

Es ist wichtig zu verstehen, dass Blöcke (Codebereiche in geschweiften Klammern) keine neuen Sichtbarkeitsbereiche erzeugen. Beim Aufruf der Funktion wird ein neuer Bereich erstellt. Das Schlüsselwort var hat einen sogenannten Funktionsumfang, keinen Blockbereich.

Wenn eine Variable im Funktionscode deklariert ist, ist sie für den gesamten Funktionscode sichtbar. Auch wenn eine Variable am Ende des Funktionscodes mit var deklariert ist, können Sie am Anfang des Codes darauf verweisen, da der Mechanismus zum Auslösen von Variablen (Heben) in JavaScript funktioniert. Dieser Mechanismus "löst" Variablendeklarationen aus, nicht jedoch die Operationen ihrer Initialisierung. Dies kann zu Verwirrung führen. Machen Sie es daher zur Regel, Variablen am Anfang einer Funktion zu deklarieren.

▍ Schlüsselwort lassen


Das Schlüsselwort let erschien in ES2015, das vereinfacht als "Block" -Version von var . Der Umfang der mit dem Schlüsselwort let deklarierten Variablen ist auf den Block, Operator oder Ausdruck, in dem er deklariert ist, sowie auf verschachtelte Blöcke beschränkt.

Wenn das Wort "let" selbst nicht sehr klar erscheint, kann man sich vorstellen, dass stattdessen das Wort "let" verwendet wird. Dann kann der Ausdruck let color = 'red' wie folgt ins Englische übersetzt werden: "let the color be red" und wie folgt ins Russische: "let the color be red".

Mit dem Schlüsselwort let können Sie die mit dem Schlüsselwort var verbundenen Mehrdeutigkeiten beseitigen (z. B. können Sie dieselbe Variable mit let nicht zweimal deklarieren). Wenn Sie let außerhalb der Funktion verwenden, z. B. beim Initialisieren von Schleifen, werden keine globalen Variablen erstellt.

Ein solcher Code verursacht beispielsweise einen Fehler:

 for (let i = 0; i < 5; i++) {   console.log(i) } console.log(i) 

Wenn bei der Initialisierung der Schleife der Zähler i mit dem Schlüsselwort var deklariert wird, ist i nach Abschluss außerhalb der Schleife verfügbar.

Heutzutage können Sie bei der Entwicklung von JS-Programmen, die auf modernen Standards basieren, var vollständig aufgeben und nur die Schlüsselwörter let und const .

▍Tastenwort const


Mit den Schlüsselwörtern var oder let deklarierte Variablen können überschrieben werden. Wenn anstelle dieser Schlüsselwörter const verwendet wird, können Sie einer mit ihrer Hilfe deklarierten und initialisierten Konstante keinen neuen Wert zuweisen.

 const a = 'test' 

In diesem Beispiel kann der Konstante a kein neuer Wert zugewiesen werden. Es sollte jedoch beachtet werden, dass die Verwendung des Schlüsselworts const dieses Objekt nicht vor Änderungen schützt, wenn a kein primitiver Wert wie eine Zahl, sondern ein Objekt ist.

Wenn sie sagen, dass ein Objekt in eine Variable geschrieben ist, meinen sie tatsächlich, dass sich die Variable auf das Objekt bezieht. Dieser Link kann nicht geändert werden, und das Objekt, zu dem der Link führt, kann geändert werden.

Das Schlüsselwort const macht Objekte nicht unveränderlich. Es schützt lediglich vor Änderungen der Verweise darauf, die in den entsprechenden Konstanten geschrieben sind. So sieht es aus:

 const obj = {} console.log(obj.a) obj.a = 1 // console.log(obj.a) //obj = 5 //  

In der obj Konstante wird bei der Initialisierung ein neues leeres Objekt geschrieben. Der Versuch, auf seine Eigenschaft a zuzugreifen, die nicht vorhanden ist, verursacht keinen Fehler. Die Konsole wird undefined . Danach fügen wir dem Objekt eine neue Eigenschaft hinzu und versuchen erneut, darauf zuzugreifen. Diesmal wird der Wert dieser Eigenschaft - 1 - an die Konsole gesendet. Wenn Sie die letzte Zeile des Beispiels auskommentieren, führt ein Versuch, diesen Code auszuführen, zu einem Fehler.

Das Schlüsselwort const ist sehr ähnlich zu let , insbesondere hat es einen Blockbereich.

Unter modernen Bedingungen ist es durchaus akzeptabel, das Schlüsselwort const zu verwenden let nur in besonderen Fällen auf let zuzugreifen und alle Entitäten zu deklarieren, deren Werte nicht geändert werden sollen. Warum? Die Sache ist, dass es am besten ist, möglichst einfache Konstruktionen zu verwenden, um Programme nicht zu komplizieren und Fehler zu vermeiden.

Datentypen


JavaScript wird manchmal als "untypisierte" Sprache bezeichnet, dies ist jedoch nicht der Fall. Es ist wahr, dass Sie Werte unterschiedlichen Typs in Variablen schreiben können, aber es gibt dennoch Datentypen in JavaScript. Insbesondere sprechen wir über primitive und Objektdatentypen.

Um den Datentyp eines bestimmten Werts zu bestimmen, können Sie den Operator typeof . Es wird eine Zeichenfolge zurückgegeben, die den Operandentyp angibt.

▍ Primitive Datentypen


Hier ist eine Liste primitiver JavaScript-Datentypen:

  • number
  • string (string)
  • boolean (Boolescher Wert)
  • null (spezieller null )
  • undefined (Sonderwert undefined )
  • symbol (Symbol, in besonderen Fällen verwendet, erschien in ES6)

Hier werden die Namen der Datentypen in der Form angegeben, in der der Operator typeof zurückgibt.

Lassen Sie uns über die am häufigsten verwendeten Datentypen aus dieser Liste sprechen.

Geben Sie die Nummer ein


Werte vom Typ number in JavaScript werden als 64-Bit-Gleitkommazahlen mit doppelter Genauigkeit dargestellt.

Im Code werden numerische Literale im Dezimalsystem als Ganz- und Bruchzahlen dargestellt. Sie können andere Methoden verwenden, um Zahlen aufzuzeichnen. Wenn zum Beispiel am Anfang eines numerischen Literal ein Präfix 0x steht, wird es als Zahl in hexadezimaler Schreibweise wahrgenommen. Zahlen können auch in Exponentialschreibweise geschrieben werden (in solchen Zahlen finden Sie den Buchstaben e ).

Hier sind Beispiele für ganzzahlige Einträge:

 10 5354576767321 0xCC //   

Hier sind die Bruchzahlen.

 3.14 .1234 5.2e4 //5.2 * 10^4 

Numerische Literale (dieses Verhalten ist auch für einige andere primitive Typen charakteristisch) werden beim Versuch, als Objekte auf sie zuzugreifen, automatisch für die Dauer der Operation in die entsprechenden Objekte konvertiert, die als "Objekt-Wrapper" bezeichnet werden. In diesem Fall handelt es sich um die Objekt-Wrapper- Number .

Hier sieht es beispielsweise wie ein Versuch aus, auf die Variable a zuzugreifen, in die ein numerisches Literal als Objekt in der Google Chrome-Konsole geschrieben ist.


Tooltip zum Umschließen von Zahlenobjekten

Wenn Sie beispielsweise die toString() -Methode eines Objekts vom Typ Number , wird eine Zeichenfolgendarstellung der Nummer zurückgegeben. Es sieht aus wie der entsprechende Befehl, der in der Browserkonsole (und im regulären Code) wie folgt ausgeführt werden kann:

 a.toString() 

Beachten Sie die doppelten Klammern nach dem Methodennamen. Wenn Sie sie nicht einfügen, gibt das System keinen Fehler aus, aber anstelle der erwarteten Ausgabe verfügt die Konsole über etwas, das nicht wie eine Zeichenfolgendarstellung der Nummer 5 aussieht.

Das globale Number Objekt kann in Form eines Konstruktors verwendet werden, der mit seiner Hilfe neue Zahlen erstellt (obwohl es in dieser Form fast nie verwendet wird). Es kann als unabhängige Entität verwendet werden, ohne Instanzen davon zu erstellen (dh einige daraus dargestellte Zahlen) Hilfe). Beispielsweise enthält die Number.MAX_VALUE Eigenschaft den maximalen numerischen Wert, der in JavaScript dargestellt werden kann.

Geben Sie string ein


Werte vom Typ string sind Zeichenfolgen. Solche Werte werden als Zeichenfolgenliterale in einfachen oder doppelten Anführungszeichen angegeben.

 'A string' "Another string" 

Zeichenfolgenwerte können mithilfe des Backslash-Zeichens in mehrere Teile aufgeteilt werden.

 "A \ string" 

Eine Zeichenfolge kann sogenannte Escape-Sequenzen enthalten, die beim Drucken der Zeichenfolge auf der Konsole interpretiert werden. Beispielsweise bedeutet die Sequenz \n ein Zeilenumbruchzeichen. Das Backslash-Zeichen kann auch verwendet werden, um Zeichenfolgen, die in demselben Anführungszeichen enthalten sind, in Anführungszeichen zu setzen. Wenn Sie das Anführungszeichen mit \ maskieren, wird es vom System nicht als Sonderzeichen wahrgenommen.

 'I\'ma developer' 

Zeichenfolgen können mit dem Operator + verkettet werden.

 "A " + "string" 

Vorlagenliterale


ES2015 führte die sogenannten Musterliterale oder Musterzeichenfolgen ein. Sie sind Zeichenfolgen, die in Backticks ( ` ) eingeschlossen sind und einige interessante Eigenschaften haben.

 `a string` 

In Vorlagenliteralen können Sie beispielsweise bestimmte Werte ersetzen, die sich aus der Auswertung von JavaScript-Ausdrücken ergeben.

 `a string with ${something}` `a string with ${something+somethingElse}` `a string with ${obj.something()}` 

Die Verwendung von Anführungszeichen erleichtert das Schreiben von mehrzeiligen Zeichenfolgenliteralen:

 `a string with ${something}` 

Geben Sie boolean ein


In JavaScript werden einige reservierte Wörter verwendet, wenn mit booleschen Werten gearbeitet wird. Diese sind true (true) und false (false). Vergleichsoperationen wie == , === , < , > geben true oder false .

Logische Ausdrücke werden in Konstrukten wie if und while , um den Fortschritt eines Programms zu steuern.

Es sollte beachtet werden, dass Sie, wenn true oder false erwartet wird, andere Werte verwenden können, die von der Sprache automatisch als wahr (wahr) oder falsch (falsch) angesehen werden.

Insbesondere sind die folgenden Werte falsch:

 0 -0 NaN undefined null '' //  

Die restlichen Werte sind wahr.

Geben Sie null ein


JavaScript hat einen speziellen null , der das Fehlen eines Werts anzeigt. Ähnliche Bedeutungen werden in anderen Sprachen verwendet.

Geben Sie undefined ein


Der in eine bestimmte Variable geschriebene undefined Wert gibt an, dass diese Variable nicht initialisiert ist und kein Wert dafür vorhanden ist.

Dieser Wert wird automatisch von Funktionen zurückgegeben, deren Ergebnisse nicht explizit mit dem Schlüsselwort return . Wenn die Funktion einen Parameter akzeptiert, der beim Aufruf nicht angegeben wird, wird er ebenfalls auf undefined .

Um den Wert für undefined zu überprüfen, können Sie die folgende Konstruktion verwenden.

 typeof variable === 'undefined' 

▍ Objekte


Alle Werte, die nicht primitiv sind, haben einen Objekttyp. Wir sprechen über Funktionen, Arrays, über das, was wir "Objekte" nennen, und über viele andere Entitäten. Alle diese Datentypen basieren auf dem object , und obwohl sie sich in vielerlei Hinsicht voneinander unterscheiden, haben sie viele Gemeinsamkeiten.

Ausdrücke


Ausdrücke sind Codefragmente, die auf der Grundlage der durchgeführten Berechnungen einen bestimmten Wert verarbeiten und erhalten können. JavaScript hat mehrere Kategorien von Ausdrücken.

Arithmetische Ausdrücke


Ausdrücke, deren Berechnungsergebnisse Zahlen sind, fallen in diese Kategorie.

 1 / 2 i++ i -= 2 i * 2 

String-Ausdrücke


Das Ergebnis der Auswertung solcher Ausdrücke sind Zeichenfolgen.

 'A ' + 'string' 'A ' += 'string' 

Primäre Ausdrücke


Literale, Konstanten und Verweise auf Bezeichner fallen in diese Kategorie.

 2 0.02 'something' true false this // ,     undefined i // i     

Dies umfasst auch einige der Schlüsselwörter und Konstruktionen von JavaScript.

 function class function* // yield // /   yield* //     async function* //   await //     /pattern/i //  () // 

Ausdrücke für die Array- und Objektinitialisierung


 [] //  {} //  [1,2,3] {a: 1, b: 2} {a: {b: 1}} 

Logische Ausdrücke


In logischen Ausdrücken werden logische Operatoren verwendet. Das Ergebnis ihrer Berechnung sind logische Werte.

 a && b a || b !a 

Eigenschaftszugriffsausdrücke


Mit diesen Ausdrücken können Sie auf die Eigenschaften und Methoden von Objekten zugreifen.

 object.property //   ( )  object[property] object['property'] 

Objekterstellungsausdrücke


 new object() new a(1) new MyRectangle('name', 2, {a: 4}) 

Funktionsdeklarationsausdrücke


 function() {} function(a, b) { return a * b } (a, b) => a * b a => a * 2 () => { return 2 } 

Rufen Sie Ausdrücke auf


Solche Ausdrücke werden verwendet, um Funktionen oder Methoden von Objekten aufzurufen.

 ax(2) window.resize() 

Mit Objekten arbeiten


Wir sind oben bereits auf Objekte gestoßen, die über Objektliterale, das Aufrufen ihrer Methoden und den Zugriff auf ihre Eigenschaften sprechen. Hier sprechen wir ausführlicher über Objekte, insbesondere den Vererbungsmechanismus des Prototyps und die Verwendung des Schlüsselworts class .

▍ Prototypvererbung


JavaScript zeichnet sich unter modernen Programmiersprachen dadurch aus, dass es die Vererbung von Prototypen unterstützt. Die meisten objektorientierten Sprachen verwenden ein klassenbasiertes Vererbungsmodell.

Jedes JavaScript-Objekt verfügt über eine spezielle Eigenschaft ( __proto__ ), die auf ein anderes Objekt verweist, das sein Prototyp ist. Ein Objekt erbt die Eigenschaften und Methoden des Prototyps.

Angenommen, wir haben ein Objekt, das mit einem Objektliteral erstellt wurde.

 const car = {} 

Oder wir haben ein Objekt mit dem Object .

 const car = new Object() 

In jedem dieser Fälle ist der Prototyp des Object.prototype .

Wenn Sie ein Array erstellen, das auch ein Objekt ist, ist sein Prototyp ein Array.prototype Objekt.

 const list = [] //  const list = new Array() 

Sie können dies wie folgt überprüfen.

 car.__proto__ == Object.prototype //true car.__proto__ == new Object().__proto__ //true list.__proto__ == Object.prototype //false list.__proto__ == Array.prototype //true list.__proto__ == new Array().__proto__ //true 

Hier haben wir die Eigenschaft __proto__ . Sie muss dem Entwickler nicht zur Verfügung stehen, aber Sie können normalerweise darauf zugreifen. Es ist zu beachten, dass eine zuverlässigere Methode zum getPrototypeOf() eines Prototyps eines Objekts die Verwendung der Methode getPrototypeOf() des globalen Object .

 Object.getPrototypeOf(new Object()) 

Alle Eigenschaften und Methoden des Prototyps sind für das Objekt mit diesem Prototyp zugänglich. Hier sieht zum Beispiel die Liste für ein Array aus.


Array-Hinweis

Der Object.prototype für alle Objekte ist Object.prototype .

 Array.prototype.__proto__ == Object.prototype 

Object.prototype keinen Prototyp.

Was wir oben gesehen haben, ist ein Beispiel für eine Prototypkette.

Wenn beim Versuch, auf eine Eigenschaft oder Methode eines Objekts zuzugreifen, das Objekt selbst nicht über eine solche Eigenschaft oder Methode verfügt, werden sie in seinem Prototyp, dann im Prototyp-Prototyp usw. gesucht, bis die gewünschte gefunden wurde oder bis Die Prototypenkette wird nicht enden.

Zusätzlich zum Erstellen von Objekten mit dem new Operator und mit Objektliteralen oder Array-Literalen können Sie eine Instanz eines Objekts mit der Object.create() -Methode erstellen. Das erste Argument, das an diese Methode übergeben wird, ist ein Objekt, das zum Prototyp des damit erstellten Objekts wird.

 const car = Object.create(Object.prototype) 

Mit der Methode isPrototypeOf() können Sie überprüfen, ob ein Objekt Teil der Prototypenkette eines anderen Objekts ist.

 const list = [] Array.prototype.isPrototypeOf(list) 

Konstruktorfunktionen


Oben haben wir neue Objekte mit den Konstruktorfunktionen erstellt, die bereits in der Sprache verfügbar sind (wenn sie aufgerufen werden, wird das new Schlüsselwort verwendet). Solche Funktionen können unabhängig voneinander erstellt werden. .

 function Person(name) { this.name = name } Person.prototype.hello = function() { console.log(this.name) } let person = new Person('Flavio') person.hello() console.log(Person.prototype.isPrototypeOf(person)) 

-. , this . name , . . - , name , .

, name , . , , , hello() . , Person hello() ( ).


ES6 JavaScript «».

JavaScript . , JS . , , , « » . , , , , , .


.

 class Person { constructor(name) {   this.name = name } hello() {   return 'Hello, I am ' + this.name + '.' } } 

, new ClassIdentifier() .

constructor , .

. hello() — , , . Person .

 const flavio = new Person('Flavio') flavio.hello() 

,


. , , , , .

, ( ) , , -, .

 class Programmer extends Person { hello() {   return super.hello() + ' I am a programmer.' } } const flavio = new Programmer('Flavio') flavio.hello() 

hello() Hello, I am Flavio. I am a programmer .

(), .

super .


, , , , , . ( static ) , .


JavaScript , (, ) . , , .


, get set . — , , . -, — .

 class Person {   constructor(name) {     this.userName = name   }   set name(value) {     this.userName = value   }   get name() {     return this.userName   } } 

Zusammenfassung


, , JavaScript. .

Liebe Leser! JS, , class.

Source: https://habr.com/ru/post/de429838/


All Articles