Im Alltag gibt es gewohnte Begriffe. In einem wissenschaftlichen Kontext können Begriffe zwar ähnlich klingen, aber doch eine spezifischere Bedeutung haben. So ist z.B. der Begriff Objekt aus der Programmiersprache A, nicht zu verwechseln ist mit einem Objekt bei B. So ist z.B. der Begriff Variable bei der Programmiersprache A nicht zu verwechseln mit einer Variablen bei B. Siehe z.B. de.wikipedia: Objektorientierte Programmierung , Funktionale Programmierung , Prototypenbasierte Programmierung und Hallo-Welt-Programme
var
bzw. int
bei C bzw. ECMAScript
// Beipspiele zu C ECMAScript // ========================================================================= int x = 6 / 5; // x-Wert ist 1 var x = 6 / 5; // x-Wert ist 1.2 // Typen, Zeiger, // fehlende Parameter möglich, // pascal-deklarierte Stackübergabe: // überzählige undefined: int simple(int* arr, int n); function simple(arr, n, p1, p2); // einheitliche Element-Typen: // unterschiedliche Element-Typen: memcpy(arr2, arr1, sizeof(int)*10); arr2 = arr1.slice(0, 10);
malloc
bei C
// Beipspiel zu C ( malloc als Boilerplate ) // ========================================================================= char *result; result = malloc( (strlen(str1) + strlen(str2) + 1) * sizeof(char) ); strcpy(result, str1 ); strcat(result, str2 ); // ... free(result);
Der Übergang von einer Programmiersprache zu einer anderen sollte nicht nur in Ähnlichkeitsbegriffen, sondern möglichst auch nativ verstanden werden:
Spezielles Schlagworte-Halbwissen in einem Bereich allein kann den Zugang zu den Möglichkeiten eines anderen Bereiches erschweren.
Douglas Crockford:
"JavaScript is the virtual machine of the Internet." und
"In gewisser Weise ist ECMAScript ein 'Lisp im C-Gewand'"
und an andere Stelle:
"JavaScript ist die erste Lambda-Sprache, die populär geworden ist."
John Lennon von den Beatles sagt es so:
"And you think you're so clever and classless and free ..."
Zu Variablblen gehören Deklarationen und eine "nativ Implementierung" ( Betriessystem, Programmiersprachen ) und Bedeutungen (siehe z.B. de.wikipedia: Deklaration_(Programmierung) ).
Zu ECMAScript gehört eine ausdrucksstarke literale Objekt-Notation und die schwache Typisierung von Datentypen. Dieses ermöglicht ausdruckstarke Schreibweisen. Eine Deklaration entspricht der Wahl eines geeigneten Bezeichners. Infolge der schwachen Typisierung kann der Wert eines ECMAScript-Bezeichners (Variablenname, Referenz) (stets) durch einen Wert jedes Datentyps überschrieben werden.
Zum (forgeschrittenen) Lernen kann es günstig sein, keine zu starre Kopplung zwischen einem Bezeichner und dem Bezeichneten zu denken. Ein ECMAScript-Bezeichner kann eine Referenz mit "Speicherplatz-Adresse" entsprechen, die auf Daten-, Objekt und Funktions-Ressource verweisen. Ändert sich bei gleichem Bezeichner Daten-Ressourcen, so ändern sich (automatisch) der interne Speicherumfang, Speicherart und die nativ-Strukturierung der Daten. Eine Zuweisung, wie z.B. var alias = obj; ist mehr eine Alias-Referenz und zunächst noch keine Tiefenkopie der Daten.
Für ECMAScript-Einsteiger, die von einer typisierten, klassenbasierten Sprache herkommen und keine hinreichende Programmiererfahrung haben gilt die "goldene Regel" von:
Douglas Crockford: "Vermeiden sienew Object
undnew Array
. Verwenden sie stattdessen{ }
und[ ]
"
Siehe z.B.
new harmful?
und
JavaScript
"New"
( yuiblog ).
Natürlich kann new
durchaus sinnvoll eingesetzt werden,
wenn die Unterschiede zu einer typisierten, klassenbasierten Sprache nativ verstanden sind
und hinreichende eigene Erfahrungen mit Stacksegment, Codesegment, Heap-Speicher vorliegen,
oder eine fachkompetent erstellte ECMAScript Bibliothek solches vorsieht.
Wie kann bei ECMAScript der "my_new-Operator" (der dem eingebauten new entspricht) definiert werden? Hier das Prinzip:
function my_new(func, args) { var that = Object.create(func.prototype), result = func.apply(that, args); return (typeof result === 'object' && result) || that; }
Texte entsprechen Zeichenketten ( Strings ). Mit einem Byte können lediglich 256 verschiedene Zeichen codiert werden. Zum weltweiten Unicode gehören mehr Zeichen.
Die Zuweisung var s = "hallo\nWelt"; verbindet die Variable s
mit der Zeichenkette "hallo\nWelt" vom Typ 'string'
und dem Prototyp-Objekt 'String' (Achtung! 1. Buchstabe von 'S
tring' wird hier groß geschrieben).
Das Prototyp-Objekt 'String' enthält die eingebauten Funktionen
und kann vom User mit neuen String-Funktionen erweitert werden.
Ein String besteht aus Zeichen, ein Zeichen entspricht nativ 2 Byte.
Ein Zeichen ist ein String.
ECMAScript verwendet intern für Strings und Zeichen das Format UTF-16. Z.B. entspricht var s = "\u0041"; dem Buchstaben "A" (siehe en.wikipedia UTF-16 ).
Die interne Speicherung von allen ECMAScript-Zahlen (Typ 'number') erfolgt intern im IEEE 754 doubble-Format (52 Bit Mantissa). Siehe typeof x liefert 'number'. de.wikipedia: Gleitkommazahl
Zu jedem Datentyp gehört die interne Speicherart und der Speicherumfang. Die Art und Bedeutung von Datentypen ist Programmiersprachenspezifisch. Hinter dem Datentyp verbergen sich nativ auf Systemebene zahlreiche Festlegungen, wie z.B. die Art der Speicherinitialisierung (static, Speicherinitialisierung beim Programmstart, dynamisch mit new im Heap, die Art der Speicherverwaltung, der Speicherbedarf, Zugriffsregeln, das betroffene Enviroment, Kontext, usw.) und bei ECMAScript z.B. auch das zugehörige Prototyp-Objekt und die zugehörigen build-in-Funktionen.
0x 0000 0000 0000 0001 = 2⁻¹⁰²²⁻⁵² ≈ 4.9406564584124654 x 10⁻³²⁴ (Min subnormal positive double) 0x 000f ffff ffff ffff = 2⁻¹⁰²² - 2⁻¹⁰²²⁻⁵² ≈ 2.2250738585072009 x 10⁻³⁰⁸ (Max subnormal positive double) 0x 0010 0000 0000 0000 = 2⁻¹⁰²² ≈ 2.2250738585072014 x 10⁻³⁰⁸ (Min normal positive double) 0x 7fef ffff ffff ffff = (1 + (1 - 2⁻⁵²)) x 2¹⁰²³ ≈ 1.7976931348623157 x 10³⁰⁸ (Max Double)
Einfache ECMAScript-Datentypen sind Zahlen (Number), Strings (String), Boolesche Werte (true, false), Null (null) und nicht definiert undefined. Alle anderen ECMAScript-Daten sind Objekte (Object). So liefert zwar typeof(myfunktion) den String 'function' und doch entspricht einer Funktion auch ein Objekt.
Bei bedingten Anweisungen sind if-Abfragen wesentlich. Merkregel für false/true Werte:
false-Werte sind: null, undefined, der leere String '' und die Number 0 true -Werte sind: der String '0', ein leerer Array [ ], ein leeres Objekt { }
Hier ein Test:
<script> var falsch = !(!null && !undefined && !'' && !0); var richtig = !(!'0' || ![] || !{} ); document.write("falsch=" + falsch + "<br />richtig=" + richtig); </script>
Ausgabe:
Das folgende Beispiel nutzt für jede Variable ein var
-Schlüsselwort.
Beispiel:
<script> var u; var x = 4711; var s1 = 'Hallo Welt'; var s2 = "<blockquote>Hallo 'ECM\u0041'-Unicode-Welt<\/blockquote>"; var obj = { x:x, s1:4712, typ:function(v){return (typeof v);} }; var ok = true; </script>
Welchen Typ haben die Variablen?
u
ist undefined.
\uxxxx
geschrieben werden.
Anstelle von var nam1 = val1; var nam2 = val2; verwendet die kompakte Schreibweise für eine Variablen-Deklaration (Definition) lediglich ein var und zwischen den Deklarationen ein Kolon als Trennzeichen.
Merkregel für kompakte Variablen-Deklarationen:
Zuweisungsoperator ist =
und das Trennzeichen zwischen den Deklarationen ist ,
und am Ende von den var
Deklarationen ist ein ;
Beispiel:
var u, x = 4711, s1 = 'Hallo Welt', s2 = "<blockquote>Hallo 'ECM\u0041'-Unicode-Welt<\/blockquote>", obj = {x:x, s1:4712, typ:function(v){return (typeof v);} } , ok = true;
Der Wert einer Variablen kann geändert werden.
Eine neue Zuweisung ändert auch den Typ der Variablen.
Der Typ einer Variablen v
kann mit (typeof v)
oder auch typeof(v) abgefragt werden.
Beipiel:
<script> var u; var x = 4711; var s1 = 'Hallo Welt'; var s2 = "<blockquote>Hallo 'ECM\u0041'-Unicode-Welt<\/blockquote>"; var obj = { x:x, s1:4712, typ:function(v){return (typeof v);} }; var ok = true; </script>
Für die Ausgabe des Variablen-Typs von v wird (typeof v) verwendet.
Die Hilfsfunktion get_types() ist im Seitenquelltext.
get_types() können mehrere Argumente (Variablen) übergeben werden.
get_types( u, x, s1, s2, ok) liefert:
Einfache ECMAScript-Datentypen sind
Zahlen (Number
),
Strings (String
),
Booesche Werte (true
, false
),
Null (null
) und nicht definiert undefined
.
Alle anderen ECMAScript-Daten sind Objekte (Object
).
Objekte sind bei ECMAScript veränderbar, über Schlüssel gebundene Sammlungen
von Daten einschließlich von Arrays, Funktionen und Objekten.
Ein Objekt-Element hat einen Property-Namen und einen Wert (key:value-Paare), etwa
var obj = { s1: 'my string1', 's2':'my string2', "dies-ist ein-zu'lässig'er Key": 'und doch recht verwirrend'};
obj
erfolgt mit obj.s1
oder mit obj['s1']
oder mit obj["s1"]
obj
erfolgt mit obj.s2
oder mit obj['s2']
oder mit obj["s2"]
obj["dies-ist ein-zu'lässig'er Key"]
oder
obj['dies-ist ein-zu"lässig"er Key']
Merkregel für Deklaration von literal Objekten var obj = { }
;
Ein Property besteht aus key und Value,
das Trennzeichen zwischen den Properties ist ,
das Trennzeichen zwischen key und Value ist :
Wichtig!
Vor der schließenden Klammer }
darf kein Komma stehen.
Im Quelltext dieser Seite ist get_types() enthalten. Die Ausgabe von
get_types( obj.x, obj['s1'], obj.typ, obj.s2 ) liefert:
Die folgende Ausgabe von
get_types( {}, [], /\s/ )
zeigt,
dass ein Typ Array, wie z.B. var arr = []; nicht existiert (es wird 'object' zurück gegeben)
und der angezeigt Typ für einen regulären Ausdruck, wie z.B. var re = /\s/; browserabhängig ist.
Anzeige:
Natürlich gehören zu aktuellen Browsern Debug-Möglichkeiten.
Doch wie kann ein einfaches objekt-Debuggen selbst programmiert werden?
Ein Objekt kann mit der for ( key in obj ) {...}
Schleife durchlaufen werden.
Mit der verfügbaren Funktion obj.hasOwnProperty(key)
kann geprüft werden,
ob key zu diesem Objekt obj gehört und nicht irgend-woher er-erbt wurde.
<script> var obj = { u:4711, o: {x:4712, y:4713}, typ:function(v){return (typeof v);} }; var obj2str = function (obj) { var key, s = "{ ", i = 0; for ( key in obj ) { if ( obj.hasOwnProperty(key) ) { if(i > 0) {s +=',<br /> ';} i += 1; s += key + ":" + obj[ key ]; } } s = '<pre>'+s +"<br />}</pre>"; return s; } document.write( obj2str(obj) ); </script>
Ausgabe von obj2str(obj
):
Ausgabe von obj2str(obj.o
):
In einer geladenen HTML-Seite stehen die
Fenster-Umgebungs-Variablen als globale Objekte zur Verfügung.
Insbesondere das window
-Objekt
und das window.document
-Objekt.
Anstelle von window.document
kann kürzer document
geschrieben werden.
Es gibt noch weitere (eigene und nativ) Umgebungsvariablen, die bei Closure behandelt werden, siehe DOM-Einfuehrung und closure-Einfuehrung .