ECMAScript | |
---|---|
Nyelvóra | A programozási nyelvek , a funkcionális programozási nyelv és a többparadigmás programozási nyelv specifikációi |
Megjelent | 1997. június |
Szerző | Brendan Eich és az Ecma International |
Fejlesztő | Brendan Eich |
Fájlkiterjesztés _ | .es[2] |
Kiadás | ECMAScript 2022 [Spec 1] (2022. június ) |
Típusrendszer | kacsa |
Dialektusok | JavaScript , JScript , ActionScript , JScript.NET , QtScript |
Befolyásolva | Self [1] , C , Scheme [1] , Perl [1] , Python , Java [1] , AWK [1] |
befolyásolta | Célkitűzés-J |
Weboldal | ecma-international.org _ |
Az ECMAScript egy beágyazható, bővíthető, I/O -t nem igénylő programozási nyelv , amely más szkriptnyelvek létrehozásának alapjául szolgál [3] .
Az ECMAScriptet az ECMA nemzetközi szervezet szabványosította az ECMA - 262 specifikációban . Nyelvi kiterjesztések: JavaScript , JScript és ActionScript .
A nyelv több technológiából származik, amelyek közül a leghíresebbek a JavaScript és a JScript nyelvek . A specifikáció első változatának kidolgozása 1996 novemberében kezdődött. A specifikációt 1997 júniusában fogadták el. Az ISO/IEC JTC 1 gyorskövetési elfogadásra benyújtva az ISO / IEC 16262 nemzetközi szabvány alapjául szolgált . 1998 júniusában az ECMA közgyűlése elfogadta az ECMA-262 második kiadását, amely megfelel az ISO / IEC 16262 szabványnak. A specifikáció harmadik kiadása a reguláris kifejezések támogatásával, a karakterláncok támogatásának javításával, új vezérlőstruktúrák bevezetésével tért el az előzőtől. , egy kivétel mechanizmus, a formázás numerikus bevitelkor és néhány egyéb változtatás[2. specifikáció] .
Az ECMAScript öt primitív adattípust támogat :
Az ECMAScript numerikus adattípusa megfelel az IEEE 754-2008 szabvány által meghatározott 64 bites lebegőpontos számformátumnak, azzal a kivétellel, hogy a szabványban [4] meghatározott különféle nem számértékek ezen a nyelven jelennek meg. az egyetlen speciális NaN értékkel [4. specifikáció] .
A nulla és definiálatlan adattípusokat informálisan "triviális" típusoknak nevezi David Flanagan , mivel mindegyik csak egy értéket határoz meg [5] .
A nyelvnek van egy "összetett" adattípusa is [5] :
A felsorolt hat adattípuson kívül az ECMAScript további hét adatot támogat, amelyeket kizárólag a kiértékelt kifejezések közbenső eredményeinek tárolására használnak:
A JavaScript nyelv népszerűsége és a különböző típusú adatok feldolgozásának nem trivialitása oda vezetett, hogy az ECMAScript adattípusok elemzése területén akadémiai kutatások indultak el, amelyek célja egy teljes értékű, integrált fejlesztésben használható kódelemző létrehozása. környezetek [6] .
Az ECMAScriptben tizenöt különböző típusú utasítás található, amelyeket az alábbi táblázat sorol fel:
A nyelvi specifikáció által meghatározott utasítástípusok [7. specifikáció]Név | eredeti név | Rövid információ | végső ; [8. specifikáció] |
---|---|---|---|
Blokk | angol Blokk | {[<utasítások>]} | − |
Változó deklaráció | angol VariableStatement | var <változódeklarációk listája> | + |
Üres utasítás | angol EmptyStatement | ; | + |
Kifejezés | angol ExpressionStatement | [string to ∉ {{, function}] utasítás | + |
Állapot | angol IfStatement | if (<инструкция>) <выражение>[ else <выражение>] | − |
Ciklus | angol IterationStatement | csináljon <kifejezést> miközben (<állítás>) while (<utasítás>) <kifejezés> |
+/- [~1] |
Folytatás | angol ContinueStatement | folytatás [<azonosító>] | + |
Megszakítás | angol BreakStatement | szünet [<azonosító>] | + |
Visszatérés | angol ReturnStatement | vissza [<utasítás>] | + |
Kombináció | angol With Statement | a (<állítás>) <kifejezéssel> | − |
Címke | angol LabelledStatement | <azonosító>: <kifejezés> | − |
Választás | angol SwitchStatement | switch (<kifejezés>) eset <utasítás>: [<kifejezések>][ eset <utasítás>: [<kifejezések>] ...] [alapértelmezett: [<kifejezések>]] | − |
Kivétel dobása | angol ThrowStatement | dobja az <utasítást> | + |
próbálja blokkolni | angol TryStatement | próbálja meg <blokk> catch (<azonosító>) <blokk> próbálja <blokk> végül <blokk> próbálja <blokk> catch (<azonosító>) <blokk> végül <blokk> |
− |
(új [Spec 9] ) Hibakereső | angol Hibakereső | hibakereső | − |
A negyedik oszlopban megjelölt esetekben a kötelező pontosvessző ellenére a specifikáció deklarál egy mechanizmust a karakterláncok pontosvesszővel történő automatikus kiegészítésére , ami oda vezet, hogy sortörés esetén a sortörés előtti utasítást ezzel a jellel lehet ellátni [ 8. specifikáció] , amely kritika tárgya [7] .
Utasítások, amelyek megváltoztatják a jelentését, ha újsort használ a [Specification 8]Példa egy utasítás jelentésének megváltoztatására
return { status : "complete" };Itt a kiemelt sor egy, a nyelvre érvényes utasítást tartalmaz, és mivel egy új sor következik, a pontosvesszővel történő automatikus kiegészítés mechanizmusa aktiválódik. Ahelyett, hogy a fenti kódot tartalmazó függvény olyan objektumot adna vissza, amelynek értéke a tulajdonság status, hanem vissza fog térni undefined.
Bár egy objektum szó szerinti formája nem egy kódblokk, az egységes zárójelek hibákhoz vezethetnek. Megfelelő kódolási szabvány kifejlesztése vagy elfogadása csökkentheti előfordulásuk valószínűségét . A behúzás stílusának megválasztása szerepet játszik . Különösen az Allman és Whitesmith stílusokat , valamint a Horstman stílust és a GNU stílust a JavaScript kódhoz a legtöbb irányelv [8] elavult , ellentétben a K&R , 1TBS , BSD KNF stílusokkal .
Az automatikus kiegészítés hibájaHa a következő sorba írt kifejezés szintaktikailag az előző sorban lévő kifejezés folytatása lehet, akkor a pontosvesszős sorok automatikus kiegészítésének mechanizmusa nem működik [9] .
func () [ 'h1' , 'h2' ]. forEach ( function ( t ) { handleTag ( t ) })Ebben a példában a második sorban lévő szögletes zárójelek a func() által visszaadott tömbelemre utalnak. A zárójelben lévő vesszőt a rendszer a megfelelő „h2”-t visszaadó operátorként kezeli. Tehát a kód a következőre lesz konvertálva:
func ()[ 'h2' ]. forEach ( function ( t ) { handleTag ( t ); });A kódolási szabványokban bevett szokás pontosvesszőket előírni akkor is, ha a nyelv szintaxisa lehetővé teszi azok elhagyását [Coding Standards 1] [Coding Standards 2] [Coding Standards 3] [Coding Standards 4] [Coding Standards 5] .
Blokkok és hatókörAz ECMAScript másik jellemzője a többi C-szerű nyelvhez képest, hogy ezen a nyelven a blokkok nem alkotnak hatókört . A blokkban deklarált változók a [10] [11] blokkot tartalmazó teljes függvényre vonatkoznak .
Ebben a kódrészletben a változót a kiemelt sorokban újra deklarálják:
function foo ( ) { varsum = 0 ; for ( var i = 0 ; i < 42 ; i += 2 ) { var tmp = i + 2 ; összeg += i * tmp ; } for ( var i = 1 ; i < 42 ; i += 2 ) { összeg += i * i ; } figyelmeztetés ( tmp ); visszatérési összeg ; _ } foo ();Ezenkívül az első ciklusban (4. sor) deklarált tmp változó a hurkon kívülről (10. sor) a nyelv szintaxisának megfelelően elérhető.
A hatókör és a blokkok természetéből adódóan a forráskód minőségének megőrzése érdekében javasolt a változók deklarálása a függvények elején [10] [Kódolási szabványok 1] [Kódolási szabványok 4] .
VáltozódeklarációkA változók meghatározása kulcsszavak segítségével történik var, let, const. Egy változó deklarálásakor függvény esetén a megfelelő hatókörbe kerül, kódblokk varesetén pedig. let, constHa egy változó a függvényeken kívül van deklarálva, akkor a globális hatókörbe kerül. Változó létrehozása akkor történik meg, amikor a függvény vezérlése a deklarációjával megérkezik. Vagy egy program, ha a változó globális. Amikor egy változót létrehozunk az ECMAScriptben, az értéket kap undefined. Ha egy változót inicializálással deklarálunk, akkor az inicializálás nem a változó létrehozásának pillanatában történik meg, hanem akkor, amikor a var[10. specifikáció] utasítást tartalmazó sort végrehajtjuk .
A kiválasztott sor megjegyzésének visszavonásakor a képernyőn nem szám jelenik meg , hanem meghatározatlan :
var a = 42 ; function foo () { alert ( typeof a ); // var a = 10; } foo ();Egy változó létrehozásakor a {DontDelete} belső tulajdonságot szerzi be, és nem törölhető a delete[Specification 10] operátor használatával . A kivétel a kontextusban deklarált változók eval[12] [11. specifikáció] .
Számos forrás [13] [14] [15] [16] [17] [18] deklarálja a változók implicit deklarálásának lehetőségét az ECMAScript-ben, amikor olyan érvényes azonosítóhoz rendelünk hozzá, amely nem formális függvényargumentum, anélkül, hogy a -val deklarálná var. A nyelvi specifikáció terminológiája szerint azonban ebben az esetben a globális objektum egy tulajdonsága jön létre, nem egy változó [12] [10. specifikáció] .
A kódolási szabványban rögzítve a változók használat előtti deklarálásának szükségességét [Coding Standards 1] [Coding Standards 4] (vagy rögzítve a névterek használatának szükségességét az összes globális objektumhoz [Coding Standards 2] ) elkerüli a finom hibákat, megelőzve a azonos nevű változók kölcsönhatása a kód különböző részeiben [19] .
A következő szavak kulcsszavak a nyelvben, és nem használhatók azonosítóként [Spec 12] :
break do instanceof typeof eset más új var elkapni végre return semmis folytassa a váltást közben debugger funkciót ezzel alapértelmezett, ha dobja törlés próbálkozás közbenA specifikáció [13. specifikáció] harmadik kiadásához képest az ötödik kiadás hozzáadott egy kulcsszót debuggera megfelelő utasítással.
A következő szavak kulcsszavakként szerepelnek a javasolt bővítményekben, ezért ezek a bővítmények adaptálásának lehetőségére vannak fenntartva [14. specifikáció] :
osztály enum kiterjeszti szuper const export importSzigorú mód használatakor a következő szavakat a rendszer a jövőbeni használatra fenntartottként kezeli [Spec 14] :
eszközök engedik a magántulajdont interfész csomag statikus védettÍgy a nyelvi specifikáció harmadik kiadásához képest jelentősen csökkent a jövőbeni használatra fenntartott szavak száma. Korábban 31 volt [15. specifikáció] , és a nagyszámú kulcsszó és fenntartott szó jelenlétét, amelyek többségét nem használják a nyelvben, kritizálták [20] .
Az ECMAScript-nek mind a kulcsszavakat, mind az írásjeleket névként használó operátorai vannak .
Operátorok osztályozásaCsökkenő sorrendben az ECMAScript operátorok a következő csoportokba oszthatók:
++A , --, -, +, ~, !, delete, typeof, void, , , ?:, =, *=, /=, +=, -=, <<=, >=operátorai >>>=jobbra asszociatívak ( vagyis &=ekvivalensek ) . A többi ECMAScript operátor asszociatív marad [22] . ^=|=a op b op ca op (b op c)
Arity szerint az ECMAScript operátorok a következő csoportokra oszthatók:
A művelet előjelének az operandusokhoz viszonyított helyzete szerint az ECMAScript operátorok a következő csoportokba sorolhatók:
Az operátorokat az operandusok típusa [25] és a végrehajtott művelet jellege szerint is osztályozzák .
Az ECMAScript utasítások jellemzőiAz ECMAScriptben nincs olyan operátor, amely lehetővé tenné annak ellenőrzését, hogy egy tulajdonság közvetlenül egy objektumhoz tartozik-e, vagy öröklődik. Ezt az ellenőrzést a hasOwnProperty(). Tekintettel arra, hogy ez a metódus nem operátor, bármely más tulajdonsággal felülírható [26] .
Az operátor +az egyetlen aritmetikai operátor a nyelvben, amely túlterhelt karakterlánc-argumentumok miatt. Ha legalább az egyik operandus karakterlánc, +akkor összefűzőként működik , ellenkező esetben összeadást hajt végre [27] [17. specifikáció] .
Azokkal a nyelvekkel ellentétben, ahol a void egy adattípus, az ECMAScript-ben ez egy operátor, amely értéket ad vissza undefined[28] .
Az operátor egy 10 lépésből álló algoritmus== szerint ellenőrzi az egyenlőséget , ami bizonyos esetekben típuskonverziót is jelent [18. specifikáció] , ami végső soron nem nyilvánvaló eredményekhez vezethet [29] .
Példa a munka eredményére ==(az összes felsorolt esetben az operátor értéke ===azonos argumentumokkal a következő lesz false):
figyelmeztetés ( "NaN" == NaN ); // téves riasztás ( NaN == NaN ); // hamis riasztás ( igaz == 1 ); // igaz figyelmeztetés ( igaz == 42 ); // téves riasztás ( null == 0 ); // téves riasztás ( 0 == "" ); // igaz figyelmeztetés ( "" == 0 ); // true alert ( "false" == hamis ); // téves riasztás ( false == 0 ); // igaz figyelmeztetés ( undefined == false ); // false alert ( null == false ); // téves riasztás ( undefined == null ); // igaz figyelmeztetés ( " \t\r\n " == 0 ); // igazAz ECMAScript függvényei objektumok [30] [31] . A konstruktor, amellyel létrehozzák őket, a Function(). A függvények, mint minden más objektum, tárolhatók változókban, objektumokban és tömbökben, átadhatók argumentumként más függvényeknek, és függvények visszaadhatják. A függvényeknek, mint minden más objektumnak, lehetnek tulajdonságai. A függvények lényeges sajátossága, hogy nevezhetők [30] .
Függvények meghatározásaAz ECMAScriptben kétféle függvény létezik:
A belső funkciók beépített objektumok (lásd alább ), amelyek nem feltétlenül az ECMAScriptben vannak implementálva [19. specifikáció] .
A program szövegében az ECMAScript elnevezett függvénye a következő módok egyikén definiálható:
// függvény deklaráció függvény összege ( arg1 , arg2 ) { return arg1 + arg2 ; } // függvény definiálása utasítással var sum2 = function ( arg1 , arg2 ) { return arg1 + arg2 ; }; // függvény meghatározása objektumjelöléssel var sum3 = new Function ( "arg1" , "arg2" , "return arg1 + arg2;" );Ez utóbbi módszer a legkevésbé preferált, mivel de facto egy függvény definiálása egy kifejezés segítségével történik, ugyanakkor a kód kettős értelmezését generálja (további értelmezés történik, amikor a kódot átadjuk a konstruktornak), ami negatívan befolyásolhatja a teljesítményt [31] .
Az első két módszer hasonló, de nem azonos hatást ad. A helyzetet rontja, hogy a függvény definiálásakor használt utasítás nagyon hasonlíthat egy függvénydeklarációhoz: egyrészt a kulcsszót functionkövetheti egy azonosító [20. specifikáció] , másrészt a pontosvessző elhagyható a karakterlánc-kiegészítő mechanizmus pontosvesszői miatt. [8. specifikáció] . Példa:
// függvény deklaráció függvény összege ( arg1 , arg2 ) { return arg1 + arg2 ; } // függvény definiálása kifejezéssel var sum2 = function sum ( arg1 , arg2 ) { return arg1 + arg2 ; } függvénysor () { }; // használja a függvénydeklarációt ( függvénysor () { }) // használja a megfelelő utasítástA függvény deklarációval történő definiálása és a függvény kifejezéssel történő definiálása között az a legjelentősebb különbség, hogy az előbbi esetben a változó létrehozása és a függvény értékként való hozzárendelése a kód végrehajtása előtt megtörténik, amikor a végrehajtási kontextusba lép. . A második esetben a változó megkapja az inicializáló értékét a hozzárendelési utasítás végrehajtásakor. Amikor egy változót a végrehajtási kontextusba való belépéskor hozunk létre, a [Spec 21] [32] értékkel inicializálódik (részletekért lásd Változódeklarációk ). undefined
Egy példa a kódvégrehajtási sorrend különbségére:
éberség ( összeg ( 3 , 4 )); // 7: a sum változó a sor végrehajtására már létrejött, és a sum ( arg1 , arg2 ) függvény hozzá lett rendelve function sum ( arg1 , arg2 ) { return arg1 + arg2 ; } riasztás ( sum2 ( 3 , 4 )); // hiba: a sum2 változó már létrejött, mire ez a sor végrehajtódik, de undefined lett hozzárendelve var sum2 = function ( arg1 , arg2 ) { return arg1 + arg2 ; };A függvénydeklarációkat nem szabad feltételes konstrukciókon belül használni [33] , bár a Gecko böngészők ezt intuitív módon kezelik a függvények utasításként megvalósított mechanizmusán keresztül [34] .
Funkció hozzárendelésekMivel az ECMAScript függvényei objektumok, azaz referencia adattípusúak , a függvényazonosítók olyan változók, amelyek a függvényre való hivatkozást tárolják. Ez a következő kóddal szemléltethető:
var összeg = függvény ( arg1 , arg2 ) { return arg1 + arg2 ; }; éberség ( összeg ( 3 , 4 )); // 7 var sum2 = sum ; riasztás ( sum2 ( 4 , 2 )); // 6 összeg = null ; figyelmeztetés ( sum2 ( 42 , 42 )); 84A kiemelt sorban ügyeljen arra, hogy ()a hozzárendelés jobb oldalán hiányzik a függvényhívás operátor ( ). Ha ebben a sorban az összeg helyett az összeg szerepelne , akkor a sum2sum() változóhoz nem függvényt rendelnénk, hanem a hívás eredményét. Egy másik dolog, amit érdemes megjegyezni, hogy a hozzárendelés után az összeg2 nem a függvény másolatára mutat, hanem arra a függvényre, amelyre az összeg mutat .
Funkció túlterhelésAz ECMAScript -ben a funkciótúlterhelés nem a nyelv tulajdonsága, hanem más mechanizmusok használatával biztosítható a hatás.
Egy példa a funkció túlterhelésének hiányára:
függvény összege ( arg1 , arg2 ) { return arg1 + arg2 ; } függvény összege ( arg1 , arg2 , arg3 ) { return arg1 + arg2 + arg3 ; } éberség ( összeg ( 3 , 4 )); // NaN alert ( összeg ( 3 , 4 , 5 )); 12Ha több, azonos nevű függvényt deklarálunk, a későbbi deklarációk felülírják a korábbi deklarációkat [31] .
A funkció túlterhelésének hatása azonban elérhető.
1. Ellenőrizze az undefined-et. Annak ellenőrzéséhez, hogy a tényleges argumentumot átadták-e a függvénynek, ellenőrizheti a formális argumentumot az azonosság értékéhez undefined. Például:
függvény összege ( arg1 , arg2 , arg3 ) { if ( arg3 !== undefined ) { return arg1 + arg2 + arg3 ; } else { return arg1 + arg2 ; } } éberség ( összeg ( 3 , 4 )); // 7 riasztás ( összeg ( 3 , 4 , 5 )); 122. Típusellenőrzés. Ezenkívül a , typeof, instanceofsegítségével constructormegtudhatja a tényleges argumentumok típusát, és ezektől függően testreszabhatja a függvény viselkedését.
function sum ( arg1 , arg2 , arg3 ) { switch ( typeof arg3 ) { case "undefined" : return arg1 + arg2 ; eset "szám" : return arg1 + arg2 + arg3 ; alapértelmezett : return arg1 + arg2 + " (" + arg3 + ")" ; } } éberség ( összeg ( 3 , 4 )); // 7 riasztás ( összeg ( 3 , 4 , 5 )); // 12 figyelmeztetés ( összeg ( 3 , 4 , "!" )); // "7 (!)"3. Hozzáférés az érvekkel kapcsolatos adatokhoz. argumentsAz ECMAScript függvényekben a [Specification 22] objektum használatával érheti el az argumentumadatokat . Konkrétan lehetővé teszi az indexelés használatát, hogy hozzáférjen a konkrét átadott argumentumokhoz [31] [35] és egy tulajdonsághoz length, amely tárolja a ténylegesen átadott argumentumok számát, ami hasznos lehet az általános programozási paradigma alkalmazásakor .
függvény összege () { var res = 0 ; for ( var i = 0 ; i < argumentumok . hossz ; i ++ ) { res += argumentumok [ i ]; } return res ; } éberség ( összeg ( 3 , 4 )); // 7 riasztás ( összeg ( 3 , 4 , 5 )); // 12 riasztás ( összeg ( 3 , 4 , 5 , 7 , 9 )); 28 RekurzióAz ECMAScript függvények rekurzív módon hívhatók. Ha utasítással határoz meg egy függvényt anélkül, hogy a függvényen belüli kulcsszó után azonosítót adna meg, akkor a [Specification 22]function objektum callee tulajdonságával hivatkozhat rá . arguments
Példa a rekurzív faktoriális számításra:
var faktoriális = függvény ( lépés , res ) { res = res || 1 ; if ( lépés < 2 ) { return res ; } visszatérési argumentumok . callee ( lépés - 1 , lépés * res ); }; riasztás ( faktoriális ( 5 )); // 120Jelenleg az ECMAScript nem valósítja meg a rekurzív hívások optimalizálására használt farokrekurziót [ 36] .
VisszahívásokAz ECMAScriptben a függvény első osztályú objektum, és argumentumként átadható egy másik függvénynek. Ha egyidejűleg abban a függvényben is meghívásra kerül, amelyiknek átadták, akkor visszahívási függvénynek (vagy visszahívási függvénynek ) nevezzük. Ha az átadott függvénynek nincs neve, akkor ez egy névtelen visszahívási függvény ( anonymous callback függvény ) [37] . A visszahívási funkciók használatának fő okai a következők:
Példa egy függvényre, amely az átadott függvény végrehajtásának eredményének összegét adja vissza az argumentumokon:
function sumOfResults ( visszahívás ) { var eredmény = 0 ; for ( var i = 1 ; i < argumentumok . hossz ; i ++ ) { eredmény += visszahívás ( argumentumok [ i ]); } eredményt ad vissza ; } var négyzet = függvény ( x ) { return x * x ; }; alert ( sumOfResults ( négyzet , 3 , 4 )); 25 LezárásokAz ECMAScript funkciói eredendően lexikális hatókörűek. Ez azt jelenti, hogy a hatókör a függvény definiálásakor van definiálva (ellentétben a dinamikus hatókörrel, ahol a hatókör a függvény meghívásakor van definiálva) [39] .
Amikor egy függvény deklarálva van, a beágyazott függvénytartományok sorozata a függvény állapotának részeként kerül tárolásra. Vagyis a programvégrehajtás során azok a függvények, amelyek hozzáférnek a befoglaló függvények helyi változóihoz, megtartják ezt a hozzáférést a program végrehajtása során [39] .
A bezárási mechanizmussal korlátozható a változók láthatósága a program egy önálló részében, hogy ne legyen névütközés más kóddal megosztva. Ehhez a kódot egy névtelen függvénybe kell helyezni, amely egy függvényhívás operátorral van ellátva.
( függvény () { // A program azon része, amelynek a változókhoz való hozzáférését kívülről el kell különíteni. })();Ebben az esetben a programrészben definiált függvények a hozzáadott névtelen függvényhez képest egymásba ágyazódnak, és elérhetővé válik az anonim függvény lokális változói (amelyek a bevezetése előtt globálisak voltak). Az anonim függvényen kívülről azonban nem érhetők el: a függvény végrehajtásának eredményét figyelmen kívül hagyja.
A lezárásokat nemcsak számos változóhoz való hozzáférés tiltására, hanem a hozzáférés módosítására is használják. Ez olyan függvényekkel érhető el, amelyek más függvényeket adnak vissza. Példa a sorozatszám generátor függvényre:
var egyediId = function () { var id = 0 ; return function () { return id ++ ; }; }(); var aValue = egyediId (); var otherValue = egyediId ();Lezárás használatával csak az egyediId változóhoz rendelt függvény férhet hozzá az id változóhoz .
Curry példa :
var multNumber = function ( arg ) { return függvény ( mul ) { return arg * mul ; }; }; var multFive = multSzám ( 5 ); riasztás ( multFive ( 7 )); //35Példa egy olyan objektum létrehozására, amely lehetővé teszi a tulajdonsághoz kizárólag annak metódusaival való hozzáférést [40] :
var myObject = function () { var érték = 0 ; return { increment : function ( inc ) { value += typeof inc === 'szám' ? inc : 1 ; }, getValue : function ( ) { return value ; } } }(); alert ( myObject . value === undefined ); // igaz figyelmeztetés ( myObject . getValue ()); // 0 myObject . növekmény ( 9 ) myObject . növekmény ( 7 ) figyelmeztetés ( myObject . getValue ()); 16Ezzel a trükkel egy lezárást használhatunk konstansok emulálására [41] .
var getConstant = function () { var konstansok = { FELSŐ_KÖTÉR : 100 , LOWER_BOUND : - 100 }; return függvény ( állandóNév ) { return állandók [ állandóNév ]; }; }(); figyelmeztetés ( getConstant ( "LOWER_BOUND" )); // -100Az ECMAScript reguláris kifejezéseinek szintaxisát és funkcionalitását a Perl 5 [Spec 23] befolyásolta, és kétféle szintaxist tesz lehetővé: literális és objektum .
var literalWay = /minta/jelzők; var objectWay = new RegExp ( minta , zászlók );Az első esetben a sablon ( pattern) és a zászlók ( ) explicit módon vannak megadva, további redundáns szintaktikai jelek nélkül: a perjelek elválasztókéntflags szolgálnak . A második esetben a sablonnak és a zászlóknak karakterlánc-értékeket tartalmazó változóknak vagy közvetlenül karakterlánc-értékeknek kell lenniük. A literális jelölést előnyben részesítjük, mivel nem igényli a reguláris kifejezés metakaraktereinek kétszeres [ ~ 2] kihagyását, ellentétben az objektum formával [42] .
A következő szimbólumok használhatók zászlóként az ECMAScriptben:
Reguláris kifejezés jelzői [42] [Spec 23]Zászló | Leírás |
---|---|
g | g globális mód: a minta minden egyezésre vonatkozik a karakterláncban, a reguláris kifejezés nem áll le a minta első egyezésének megtalálása után |
i | és kis- és nagybetűk figyelmen kívül hagyása : egyeztetéskor a minta karaktereinek és karakterláncainak kis- és nagybetűit figyelmen kívül hagyja |
m | többsoros mód: az újsor karaktereket tartalmazó sort a rendszer több sorként kezeli, amelyeket soremelés karakterek választanak el egymástól; a regex minden vonalon működik |
Minden reguláris kifejezés egy objektum a következő tulajdonságokkal:
ECMAScript reguláris kifejezés objektum tulajdonságai [42] [23. specifikáció]Ingatlan | Típusú | Leírás |
---|---|---|
global | logikus | megmutatja, hogy a zászló be van-e állítvag |
ignoreCase | logikus | megmutatja, hogy a zászló be van-e állítvai |
multiline | logikus | megmutatja, hogy a zászló be van-e állítvam |
lastIndex | számszerű | megegyezik a karakterlánc pozíciószámával , ahol a minta egyezést talált a reguláris kifejezés előző alkalmazása eredményeként, vagy 0, ha a reguláris kifejezést korábban nem alkalmazták |
source | húr | a reguláris kifejezés mintájának megfelelő karakterláncot |
Ezenkívül a következő módszerek vannak definiálva a reguláris kifejezésekhez:
Reguláris kifejezés objektum metódusai az ECMAScriptben [42] [23. specifikáció]Módszer | visszatérési típus | Leírás |
---|---|---|
exec(handledString) | objektum (tömb) illnull | a megadott mintának megfelelő alsztringek tömbjét képezi , figyelembe véve a beállított jelzőket . nullha egyetlen részkarakterlánc sem felel meg a mintának |
test(handledString) | logikus | trueha van a mintához illő karakterlánc és falseegyébként |
Az ECMAScript-objektumok tulajdonságok rendezetlen gyűjteményei , amelyek mindegyike rendelkezik egy vagy több attribútummal , amelyek meghatározzák a tulajdonság használatának módját – például, ha az ReadOnly attribútum értéke igaz , akkor az ECMAScript-kód végrehajtásával végrehajtott minden kísérlet a tulajdonság megváltoztatására. az ingatlan értéke tönkremegy. A tulajdonságok olyan tárolók , amelyek más objektumokat, primitív típusok értékeit és metódusokat foglalnak magukba [24. specifikáció] .
ECMAScript objektumtulajdonság attribútumok [Spec 25]Név | Leírás |
---|---|
csak olvasható | Az ingatlan csak olvasható. A programban tett kísérlet ennek az ingatlannak az értékének megváltoztatására hiábavaló marad. Egyes esetekben egy ReadOnly attribútumkészlettel rendelkező tulajdonság értéke megváltozik a nyelvi kiterjesztési környezet műveletei miatt, ezért az ReadOnly nem értelmezhető megváltoztathatatlannak. |
DontEnum | A tulajdonság nincs felsorolva hurokkalfor-in |
Ne törölje | A rendszer figyelmen kívül hagyja a tulajdonság eltávolítására tett kísérleteket. |
Belső | Az ingatlan belső. Ennek nincs neve, és nem érhető el férőhelyekkel . Ezekhez a tulajdonságokhoz való hozzáférést a nyelvi megvalósítás határozza meg. |
Az ECMAScript objektumok alapvető (natív) és kiterjesztés (host) objektumokra oszthatók . Bázis alatt minden olyan objektumot értünk, amely független a nyelv kiterjesztéséhez kapcsolódó környezettől. Az alapvető objektumok egy része beépített : a program végrehajtásának legelejétől létező. Mások is létrehozhatók a program futása közben. A kiterjesztésobjektumokat az ECMAScript kiterjesztés biztosítja, és az ECMAScript esetében ez azt jelenti, hogy a Dokumentumobjektum-modell vagy a Böngészőobjektum-modell részét képezik [3. specifikáció] .
SzintaxisObjektum és literális formák használhatók objektumok megadására. Az objektumokat megadó objektumformák szintaxisa hasonló a Java-hoz, de ezzel ellentétben az ECMAScript-ben csak akkor kell zárójeleket használni, amikor argumentumokat adunk át a konstruktornak [43] . A következő bejegyzések szintaktikailag egyenértékűek:
varobj1 = új objektum ( ); var obj2 = new Object ; var obj3 = {};A második lehetőség azonban nem ajánlott [43] . Douglas Crockford az első lehetőség mellőzését is javasolja, inkább a szó szerinti formát részesítse előnyben, amit a nyelv nagy előnyének tart [44] .
A nyelvi specifikáció az objektum tulajdonságának fogalmával operál, egy metódust az objektum tulajdonságaként használt függvénynek nevezve [3. specifikáció] .
A nyelv minden objektumának a következő tulajdonságai vannak:
ECMAScript objektumok tulajdonságai [43]Név | Rövid leírás |
---|---|
constructor | Az objektum létrehozásához használt függvény (a fenti példákban ez Object()) |
rendelkezik saját tulajdonnal(tulajdonnév) | Azt jelzi, hogy az adott tulajdonság létezik-e az objektumban (nem a prototípusában ) |
isPrototypeOf(objektum) | Meghatározza, hogy egy objektum szerepel-e az argumentumobjektum prototípusláncában |
propertyIsEnumerable(tulajdonságnév) | Azt jelzi, hogy a megadott nevű tulajdonság felsorolható-e a ciklusbanfor-in |
toString() | Az objektum karakterlánc reprezentációját adja vissza |
értéke() | Ezt az értéket adja vissza . Ha az objektum egy kiterjesztési objektum konstruktorának hívásának eredménye , az érték valueOf()megvalósításfüggő [Spec 26] . A visszatérési érték gyakran egy objektumnak megfelelő primitív típusú érték. Ennek a módszernek az eredménye általában ugyanaz, mint a toString(). A konstruktorral létrehozott objektumok Date() kiváló példák arra, ahol a toString()és az eredmények valueOf()nem egyeznek [43] . |
Az objektumtulajdonságok pont és zárójel jelöléssel érhetők el:
var obj = new Object (); alert ( obj . konstruktor === obj [ "konstruktor" ]); // igaz - a tulajdonság eléréséhez használjon pont és zárójel jelölést var foo = obj [ "toString" ]; // zárójel jelöléssel a függvényt változóban tároljuk var result = obj [ "toString" ](); // a függvényhívás eredményének mentése egy változó riasztásba ( foo ()); // a tárolt függvény meghívásának eredményének megjelenítése a képernyőn alert ( eredmény ); varboo = obj . _ toString ; // hasonló pontjelöléssel var res = obj . toString (); éber ( bú ()); éber ( res );Az új tulajdonságok dinamikusan állíthatók be.
varcountry = new Object ( ); ország [ "név" ] = "Oroszország" ; // használja a zárójelben szereplő ország jelölését . alapítási év = 862 ; // pont jelölés használata var country2 = { "név" : "Oroszország" , "alapítási év" : 862 }; // szó szerinti alak használataAz előző részben leírt módon objektumok létrehozása nem lehet praktikus a kód megkettőzésének szükségessége miatt [45] . Ha a program nagyszámú azonos típusú objektumot kezel, a fejlesztőnek lehetősége van kiválasztani a nyelvben használt technikák egyikét [45] :
tárgygyár egy függvény, amely létrehoz egy objektumot és visszaadja azt értékeként, konstruktőr egy függvény, amely a kulcsszó thissegítségével alakítja ki az általa létrehozott objektum tulajdonságait az operátor segítségével new, prototípus megközelítés egy függvény tulajdonságának prototypefelhasználása az objektumok általános tulajdonságainak megjelenítésére, vegyes megközelítésű konstruktor-prototípus konstruktor használata olyan objektumok tulajdonságainak beállítására, amelyek nem metódusok, és prototípus megközelítés a metódusok beállításához, dinamikus prototípus módszer a vegyes konstruktor-prototípus megközelítésen alapuló objektumok létrehozási funkciójához kapcsolódó kód egy funkcióba zárása, biztosítva a prototípus tulajdonságok egyszeri hozzárendelését, parazita konstruktor módszer newobjektumgyári funkcióval használható .A nyelvben nincsenek osztályok , de konstruktorokkal emulálhatók. Példa osztályemulációra az ECMAScriptben:
function MyClass () { this . myValue1 = 1 ; ezt . myValue2 = 2 ; } osztályom . prototípus . myMethod = function () { return this . myValue1 * ez . myValue2 ; } var mc = new MyClass (); mc . myValue1 = mc . myValue2 * 2 ; var i = mc . myMethod ();Az objektum minden egyes összetevőjénél figyelembe lehet venni az öröklődést. Amikor egy szülő interfészét örököljük anélkül, hogy a gyermek az ős funkcionalitását használja, akkor az interfész öröklődéséről beszélünk. Állapot öröklésekor a gyermekobjektum örökli az ősobjektum adatstruktúráját. A funkcionalitás öröklésekor az interfész és a metóduskód mellett öröklődésről beszélünk. Ez általában magában foglalja az állapotöröklés megszervezésének szükségességét, ami indokolttá teszi az állapotöröklődés és a funkcionalitás öröklődés összekapcsolását implementációs öröklődéssé [46] .
Az ECMAScript esetében csak az interfész öröklődése nem érvényes, mivel a nyelv függvényei nem rendelkeznek aláírással [45] .
A nyelv adta lehetőségeket az öröklés megszervezésére például a Sztojan Stefanov [47] által adott tizenkét különböző öröklésszervezési módot tartalmazó lista alapján ítélhetjük meg.
Az ES6 elfogadása számos JavaScript-probléma osztályt kiküszöbölt [48] [49] [50] [51] .
ECMAScript | |||||||||||||
---|---|---|---|---|---|---|---|---|---|---|---|---|---|
Dialektusok | |||||||||||||
Motorok ( összehasonlítás ) | |||||||||||||
Keretrendszerek , könyvtárak |
| ||||||||||||
Emberek | |||||||||||||
Egyéb |
Ecma nemzetközi szabványok | |
---|---|
ISO szabványok | |
---|---|
| |
1 -től 9999 -ig |
|
10 000 és 19999 között |
|
20000+ | |
Lásd még: Azon cikkek listája, amelyek címe "ISO"-val kezdődik |