¿Qué hace "uso estricto" en JavaScript, y cuál es el razonamiento detrás de esto?

7549

Recientemente, ejecuté parte de mi código JavaScript a través de JSLint de Crockford , y me dio el siguiente error:

Problema en la línea 1, carácter 1: Falta la declaración "use estricto".

Al hacer algunas búsquedas, me di cuenta de que algunas personas agregan "use strict";su código JavaScript. Una vez que agregué la declaración, el error dejó de aparecer. Desafortunadamente, Google no reveló gran parte de la historia detrás de esta declaración de cadena. Ciertamente debe tener algo que ver con la forma en que el navegador interpreta el JavaScript, pero no tengo idea de cuál sería el efecto.

Entonces, ¿de qué se "use strict";trata, qué implica y sigue siendo relevante?

¿Alguno de los navegadores actuales responde a la "use strict";cadena o es para uso futuro?

Mark Rogers
fuente
55
Las respuestas aquí son viejas pero están equivocadas. El razonamiento principal para el modo estricto no era evitar errores de programación: era hacer que JavaScript tuviera un alcance léxico para que pudiera analizarse estáticamente:]
Benjamin Gruenbaum,
@BenjaminGruenbaum Usar "use strict";solo no hace que JS tenga un alcance léxico. Declarar variables con lety también constdebe usarse.
Koorosh Pasokhi
Está mezclando entre ámbito de bloque y ámbito léxico.
Benjamin Gruenbaum

Respuestas:

4938

Este artículo sobre Javascript Strict Mode puede interesarle: John Resig - ECMAScript 5 Strict Mode, JSON y más

Para citar algunas partes interesantes:

El modo estricto es una nueva característica en ECMAScript 5 que le permite colocar un programa o una función en un contexto operativo "estricto". Este contexto estricto evita que se tomen ciertas acciones y genera más excepciones.

Y:

El modo estricto ayuda de dos maneras:

  • Captura algunos bloopers de codificación comunes, arrojando excepciones.
  • Previene, o arroja errores, cuando se toman acciones relativamente "inseguras" (como obtener acceso al objeto global).
  • Deshabilita características que son confusas o mal pensadas.

También tenga en cuenta que puede aplicar el "modo estricto" a todo el archivo ... O puede usarlo solo para una función específica (todavía citando el artículo de John Resig) :

// Non-strict code...

(function(){
  "use strict";

  // Define your library strictly...
})();

// Non-strict code... 

Lo que podría ser útil si tiene que mezclar código antiguo y nuevo ;-)

Entonces, supongo que es un poco como el "use strict"que puedes usar en Perl (¿de ahí el nombre?) : Te ayuda a cometer menos errores al detectar más cosas que podrían provocar roturas.

El modo estricto ahora es compatible con todos los principales navegadores .

Dentro de los módulos nativos de ECMAScript (con importy exportdeclaraciones) y clases de ES6 , el modo estricto siempre está habilitado y no se puede deshabilitar.

Pascal MARTIN
fuente
100
¿Cambiar el valor predeterminado después de tantos años? Demasiado tarde para eso: rompería tantos sitios / scripts / aplicaciones existentes ... Lo único posible es ayudar a mejorar las cosas, para el futuro.
Pascal MARTIN
14
Probé un pequeño fragmento de código que no sería válido al usar "use strict"en Firefox 3.6, Safari 5, Chrome 7 y Opera 10.6 (todos Mac). No hay errores de ningún tipo, así que supongo que 'usar estricto' aún no es compatible con ningún navegador. Sin embargo, no probé en IE9;)
Husky
11
Actualización rápida: Firefox 4 tiene soporte completo para el modo estricto, y por lo que puedo decir, ningún otro navegador lo hace. Safari y Chrome tienen soporte "parcial", pero realmente no sé qué significa eso.
Sasha Chedygov
29
Chrome 11 parece pasar todas estas pruebas al igual que IE10, es decir
microsoft.com/testdrive/HTML5/
12
@Julius: esto no podría haberse implementado usando una palabra clave reservada, porque el código que intenta activar el modo estricto se rompería en los navegadores antiguos. Agregar un literal de cadena "aleatorio" no rompe nada.
nnnnnn
1245

Es una nueva característica de ECMAScript 5. John Resig escribió un buen resumen del mismo.

Es solo una cadena que coloca en sus archivos JavaScript (ya sea en la parte superior de su archivo o dentro de una función) que se ve así:

"use strict";

Ponerlo en su código ahora no debería causar ningún problema con los navegadores actuales, ya que es solo una cadena. Puede causar problemas con su código en el futuro si su código viola el pragma. Por ejemplo, si actualmente tiene foo = "bar"sin definir fooprimero, su código comenzará a fallar ... lo cual es algo bueno en mi opinión.

seth
fuente
329
Falla rápido y falla en voz alta.
Niels Bom
31
Si está escribiendo Javascript en línea en archivos HTML, comience cada nuevo bloque con <script>"use strict";. La bandera solo se aplica al bloque en el que está incluida.
nobar
77
Es curioso, esto resultó en que las cadenas deben tener comillas simples. Así que escriba en su 'use strict';lugar
nilsi
1
entonces, ¿qué pasaría con el concepto de elevación de javascript?
Sunil Sharma
1
@SunilSharma Si intenta elevar, pero falla porque la variable no está definida, en este momento la agregará al objeto global. Con "use strict";, fallará en su lugar. Esto tiene más sentido, porque si lo agrega al objeto global, eso significa que podría no funcionar la próxima vez que ejecute la función / haga otra cosa que restablezca el bloque, ya que estará en el bloque más alto (global).
wizzwizz4
646

La declaración "use strict"; indica al navegador que use el modo Estricto, que es un conjunto de funciones reducido y más seguro de JavaScript.

Lista de características (no exhaustivas)

  1. No permite variables globales. (Captura vardeclaraciones y errores tipográficos faltantes en nombres de variables)

  2. Las tareas fallidas silenciosas arrojarán errores en modo estricto (asignación NaN = 5;)

  3. Los intentos de eliminar propiedades no recuperables arrojarán ( delete Object.prototype)

  4. Requiere que todos los nombres de propiedad en un objeto literal sean únicos ( var x = {x1: "1", x1: "2"})

  5. Los nombres de los parámetros de la función deben ser únicos ( function sum (x, x) {...})

  6. Prohíbe la sintaxis octal ( var x = 023;algunos desarrolladores suponen erróneamente que un cero anterior no hace nada para cambiar el número).

  7. Prohíbe la withpalabra clave

  8. eval en modo estricto no introduce nuevas variables

  9. Prohíbe eliminar nombres simples ( delete x;)

  10. Prohíbe la vinculación o asignación de los nombres evaly argumentsen cualquier forma

  11. El modo estricto no alias las propiedades del argumentsobjeto con los parámetros formales. (es decir, en function sum (a,b) { return arguments[0] + b;}Esto funciona porque arguments[0]está vinculado, aetc.)

  12. arguments.callee no es apoyado

[Ref: Modo estricto , Red de desarrolladores de Mozilla ]

gprasant
fuente
40
Nit: las variables globales están permitidas, solo tienen que ser explícitas (por ejemplo window.foo = bar).
gcampbell
1
Requiere que todos los nombres de propiedad en un objeto literal sean únicos (var x = {x1: "1", x1: "2"}) es válido
Arun Killu
44
A su ejemplo en 11 le falta una modificación de a (de lo contrario, no tiene sentido). I. e. función suma (a, b) {a = 0; devuelve argumentos [0] + b; } alert (sum (1, 2)) devolverá 3 con modo estricto y 2 sin modo estricto, debido a alias.
David Gausmann
413

Si a las personas les preocupa usar use strict , puede valer la pena leer este artículo:

Compatibilidad con 'Modo estricto' de ECMAScript 5 en navegadores. ¿Qué significa esto?
NovoGeek.com - el weblog de Krishna

Habla sobre el soporte del navegador, pero lo más importante es cómo tratarlo de manera segura:

function isStrictMode(){
    return !this;
} 
/*
   returns false, since 'this' refers to global object and 
   '!this' becomes false
*/

function isStrictMode(){   
    "use strict";
    return !this;
} 
/* 
   returns true, since in strict mode the keyword 'this'
   does not refer to global object, unlike traditional JS. 
   So here, 'this' is 'undefined' and '!this' becomes true.
*/
Jamie Hutber
fuente
116
Estoy en desacuerdo. Creo que esto muestra por qué es muy útil. En esencia, significa que esto devuelve su función y no elwindow
Jamie Hutber
36
¿Cuándo quieres la ventana con la thisque no puedes apuntar window?
Jamie Hutber
14
Se refiere a sí mismo. thispertenece a su propia función y no a la ventana global
Jamie Hutber
26
En el segundo thisuno es en realidad undefined.
Broxzier
14
El punto es que su programa JS comenzará a fallar debido al acceso a una propiedad de un indefinido, en lugar de hacer silenciosamente lo incorrecto en el objeto global. Hace que rastrear errores sutiles sea mucho más fácil.
Stephen Chung
208

Una advertencia: todos ustedes, programadores de carga dura: ¡aplicar "use strict"al código existente puede ser peligroso! Esta cosa no es una calcomanía para sentirse bien, una cara feliz que puede colocar en el código para que sea 'mejor'. Con el "use strict"pragma, el navegador de repente LANZARÁ excepciones en lugares aleatorios que nunca arrojó antes solo porque en ese punto estás haciendo algo que JavaScript predeterminado / suelto permite felizmente, ¡pero aborrece estrictamente JavaScript! Es posible que tenga infracciones de rigurosidad ocultas en llamadas poco utilizadas en su código que solo arrojarán una excepción cuando finalmente se ejecuten, por ejemplo, en el entorno de producción que usan sus clientes de pago.

Si va a dar el paso, es una buena idea aplicar "use strict"junto con pruebas de unidad integrales y una tarea de construcción JSHint estrictamente configurada que le dará cierta confianza de que no hay un rincón oscuro de su módulo que explotará horriblemente solo porque usted He activado el modo estricto. O, hey, aquí hay otra opción: simplemente no agregue "use strict"a ninguno de sus códigos heredados, probablemente sea más seguro de esa manera, honestamente. DEFINITIVAMENTE NO agregue "use strict"a ningún módulo que no posea o mantenga, como los módulos de terceros.

Creo que a pesar de que es un animal enjaulado mortal, "use strict"puede ser algo bueno, pero hay que hacerlo bien. El mejor momento para ser estricto es cuando su proyecto es totalmente nuevo y comienza desde cero. Realice la configuración JSHint/JSLintcon todas las advertencias y opciones tan ajustadas como su equipo pueda soportar, obtenga un buen sistema de construcción / prueba / afirmación del mismo modo Grunt+Karma+Chai, y solo ENTONCES comience a marcar todos sus módulos nuevos como "use strict". Esté preparado para curar muchos errores y advertencias molestos. Asegúrese de que todos entiendan la gravedad configurando la compilación para FALLAR si JSHint/JSLintproduce alguna violación.

Mi proyecto no era un proyecto nuevo cuando lo adopté "use strict". Como resultado, mi IDE está lleno de marcas rojas porque no tengo la "use strict"mitad de mis módulos, y JSHint se queja de eso. Es un recordatorio para mí sobre la refactorización que debo hacer en el futuro. Mi objetivo es estar libre de marcas rojas debido a todas mis "use strict"declaraciones faltantes , pero eso está a años de distancia.

DWoldrich
fuente
24
¿POR QUÉ los desarrolladores en este hilo son tan arrogantes sobre "usar estricto"? ¡LANZA EXCEPCIONES en JavaScript que de otro modo funcionaría , por el amor de Dios! Solo espolvorea en el código como el azúcar en Corn Flakes, ¿eh? ¡NO! ¡MALO! "use estricto" se debe usar con precaución, preferiblemente solo en el código que controle que tenga pruebas unitarias que pasen contra todos los principales navegadores y que ejerzan todas las rutas de código. Tienes pruebas? De acuerdo, "usar estricto" está bien para ustedes, noqueen.
DWoldrich
57
Si. Obviamente "usar estricto" puede romper JavaScript aparentemente válido que no se ha roto antes. Pero el código que no se ha roto antes no es igual a que el código sea correcto y haga lo que se supone que debe hacer. Por lo general, hacer referencia a variables no declaradas señala un error tipográfico, etc. El uso estricto le permite detectar este tipo de errores y, con suerte, antes de enviar el código de producción.
Jostein Kjønigsen
55
... o simplemente aplique "use estricto" como parte de un último paso sobre su código, solucione todos los problemas obvios, encoja los hombros, diga "lo suficientemente bueno", luego sáquelo para producción :)
Wolfie Inu
13
Personalmente, nunca / muy rara vez agrego "use strict"; código existente. Dicho esto, casi siempre lo uso cuando escribo un nuevo código desde cero
Martin
3
Sin embargo, si ya está utilizando JSLint, probablemente haya arreglado la mayoría de los lugares donde "usar estricto" rompería las cosas.
Jonathan Cast
179

El uso 'use strict';no mejora repentinamente su código.

El modo estricto de JavaScript es una característica de ECMAScript 5 . Puede habilitar el modo estricto declarándolo en la parte superior de su script / función.

'use strict';

Cuando un motor de JavaScript ve esta directiva , comenzará a interpretar el código en un modo especial. En este modo, se producen errores cuando se detectan ciertas prácticas de codificación que podrían terminar siendo posibles errores (que es el razonamiento detrás del modo estricto).

Considere este ejemplo:

var a = 365;
var b = 030;

En su obsesión por alinear los literales numéricos, el desarrollador ha inicializado inadvertidamente la variable bcon un literal octal. El modo no estricto interpretará esto como un literal numérico con valor 24(en base 10). Sin embargo, el modo estricto arrojará un error.

Para obtener una lista no exhaustiva de especialidades en modo estricto, consulte esta respuesta .


¿Dónde debo usar 'use strict';?

  • En mi nuevo aplicación de JavaScript: ¡Absolutamente! El modo estricto se puede utilizar como denunciante cuando estás haciendo algo estúpido con tu código.

  • En mi código JavaScript existente : ¡ Probablemente no! Si su código JavaScript existente tiene declaraciones que están prohibidas en modo estricto, la aplicación simplemente se interrumpirá. Si desea un modo estricto, debe estar preparado para depurar y corregir su código existente. Esta es la razón por la que el uso 'use strict';no mejora repentinamente su código .


¿Cómo uso el modo estricto?

  1. Insertar un 'use strict'; declaración en la parte superior de su script:

    // File: myscript.js
    
    'use strict';
    var a = 2;
    ....

    Tenga en cuenta que todo en el archivo myscript.js se interpretará en modo estricto.

  2. O inserte un 'use strict'; declaración en la parte superior del cuerpo de su función:

    function doSomething() {
        'use strict';
        ...
    }

    Todo en el ámbito léxico de la función doSomethingse interpretará en modo estricto. La palabra alcance léxico es importante aquí. Por ejemplo, si su código estricto llama a una función de una biblioteca que no es estricta , solo su código se ejecuta en modo estricto, y no la función llamada. Vea esta respuesta para una mejor explicación.


¿Qué cosas están prohibidas en modo estricto?

Encontré un buen artículo describe varias cosas que están prohibidas en modo estricto (tenga en cuenta que esta no es una lista exclusiva):

Alcance

Históricamente, JavaScript se ha confundido sobre cómo se definen las funciones. A veces parecen tener un alcance estático, pero algunas características hacen que se comporten como si estuvieran en un alcance dinámico. Esto es confuso, lo que hace que los programas sean difíciles de leer y comprender. El malentendido causa errores. También es un problema para el rendimiento. El alcance estático permitiría que se produzca un enlace variable en tiempo de compilación, pero el requisito de alcance dinámico significa que el enlace debe diferirse al tiempo de ejecución, lo que conlleva una penalización de rendimiento significativa.

El modo estricto requiere que todo el enlace variable se realice de forma estática. Eso significa que las características que anteriormente requerían enlace dinámico deben eliminarse o modificarse. Específicamente, se elimina la instrucción with, y la capacidad de la función eval de alterar el entorno de su interlocutor está severamente restringida.

Uno de los beneficios del código estricto es que las herramientas como YUI Compressor pueden hacer un mejor trabajo al procesarlo.

Variables globales implícitas

JavaScript ha implicado variables globales. Si no declara explícitamente una variable, una variable global se declara implícitamente por usted. Esto facilita la programación para principiantes porque pueden descuidar algunas de sus tareas básicas de limpieza. Pero hace que la administración de programas más grandes sea mucho más difícil y degrada significativamente la confiabilidad. Entonces, en modo estricto, las variables globales implícitas ya no se crean. Debe declarar explícitamente todas sus variables.

Fuga global

Hay una serie de situaciones que podrían hacer this que se vincule al objeto global. Por ejemplo, si olvida proporcionar el newprefijo al llamar a una función de constructor, los del constructor thisse vincularán inesperadamente al objeto global, por lo que en lugar de inicializar un nuevo objeto, en su lugar estará manipulando silenciosamente las variables globales. En estas situaciones, el modo estricto se unirá thisa undefined, lo que hará que el constructor arroje una excepción, permitiendo que el error se detecte mucho antes.

Fracaso ruidoso

JavaScript siempre ha tenido propiedades de solo lectura, pero no puede crearlas usted mismo hasta que la Object.createProperty función de ES5 expone esa capacidad. Si intentó asignar un valor a una propiedad de solo lectura, fallaría en silencio. La asignación no cambiaría el valor de la propiedad, pero su programa procedería como si lo hubiera hecho. Este es un peligro para la integridad que puede hacer que los programas entren en un estado inconsistente. En modo estricto, intentar cambiar una propiedad de solo lectura generará una excepción.

Octal

La representación octal (o base 8) de los números fue extremadamente útil cuando se realizaba la programación a nivel de máquina en máquinas cuyos tamaños de palabra eran múltiplos de 3. Se necesitaba octal al trabajar con el mainframe CDC 6600, que tenía un tamaño de palabra de 60 bits. Si pudieras leer octal, podrías mirar una palabra como 20 dígitos. Dos dígitos representaban el código operativo, y un dígito identificaba uno de los 8 registros. Durante la transición lenta de códigos de máquina a lenguajes de alto nivel, se pensó que era útil proporcionar formas octales en lenguajes de programación.

En C, se seleccionó una representación extremadamente desafortunada de octalidad: cero inicial. Entonces, en C, 0100significa 64, no 100, y 08es un error, no 8. Aún más desafortunadamente, este anacronismo se ha copiado en casi todos los lenguajes modernos, incluido JavaScript, donde solo se usa para crear errores. No tiene otro propósito. Entonces, en modo estricto, las formas octales ya no están permitidas.

Etcétera

Los argumentos pseudo array se vuelven un poco más parecidos a un array en ES5. En modo estricto, pierde sus calleey sus caller propiedades. Esto hace posible pasar su argumentscódigo no confiable sin renunciar a mucho contexto confidencial. Además, argumentsse elimina la propiedad de las funciones.

En modo estricto, las claves duplicadas en un literal de función producirán un error de sintaxis. Una función no puede tener dos parámetros con el mismo nombre. Una función no puede tener una variable con el mismo nombre que uno de sus parámetros. Una función no puede tener deletesus propias variables. Un intento de deleteuna propiedad no configurable ahora arroja una excepción. Los valores primitivos no están implícitamente envueltos.


Palabras reservadas para futuras versiones de JavaScript

ECMAScript 5 agrega una lista de palabras reservadas. Si los usa como variables o argumentos, el modo estricto arrojará un error. Las palabras reservadas son:

implements, interface, let, package, private, protected, public, static, Yyield


Otras lecturas

sampathsris
fuente
2
Es una muy buena explicación. Sin embargo, tengo una duda de que puedo usar el modo "estricto" junto con otras bibliotecas de script java, como Angular js.
UVM
3
@UVM: la directiva de modo estricto solo afecta el alcance léxico. es decir, solo el archivo / función que se declara. Si tiene otro archivo / función que no tiene la 'use strict'directiva, se ejecutarán en modo no estricto, incluso cuando se llama desde una función que se ejecuta en modo estricto. Vea esta respuesta para una explicación.
sampathsris
Esto no es del todo correcto. 'use estricto' cambia la forma en que se ejecuta el código.
CyberEd
3
En la segunda mirada, tienes razón. Pensé que querías decir que solo arrojó excepciones, pero no cambió la forma en que funcionaba el código (como cambiar this). Ahora veo que te referías a llamar a otras funciones.
CyberEd el
3
Hay algunos casos en los que el octal es útil. La sintaxis de C es horrible, pero me hubiera gustado ver que los lenguajes agregan una nueva sintaxis octal que podría permitir que la forma de cero inicial quede en desuso. Por supuesto, para Javascript haber admitido la forma de cero a la izquierda fue una tontería.
supercat
138

Recomiendo encarecidamente a cada desarrollador que comience a usar el modo estricto ahora. Hay suficientes navegadores que lo admiten que el modo estricto legítimamente nos ayudará a salvarnos de errores que ni siquiera sabíamos que estaban en su código.

Aparentemente, en la etapa inicial habrá errores que nunca hemos encontrado antes. Para obtener el beneficio completo, debemos realizar las pruebas adecuadas después de cambiar al modo estricto para asegurarnos de que hemos captado todo. Definitivamente no solo agregamos use strictnuestro código y asumimos que no hay errores. Entonces, el abandono es que es hora de comenzar a usar esta función de lenguaje increíblemente útil para escribir un mejor código.

Por ejemplo,

var person = {
    name : 'xyz',
    position : 'abc',
    fullname : function () {  "use strict"; return this.name; }
};

JSLint es un depurador escrito por Douglas Crockford. Simplemente pegue su script, y escaneará rápidamente en busca de problemas y errores notables en su código.

Pank
fuente
66
@JamieHutber: visite este enlace caniuse.com/use-strict AND kangax.github.io/es5-compat-table . Le dará una idea exacta para todos los navegadores.
Pank
95

Me gustaría ofrecer una respuesta algo más fundada que complemente las otras respuestas. Esperaba editar la respuesta más popular, pero fallé. Traté de hacerlo lo más completo y completo posible.

Puede consultar la documentación de MDN para obtener más información.

"use strict" Una directiva introducida en ECMAScript 5.

Las directivas son similares a las declaraciones, pero diferentes.

  • use strictno contiene palabras clave: la directiva es una declaración de expresión simple, que consiste en un literal de cadena especial (entre comillas simples o dobles). Los motores de JavaScript, que no implementan ECMAScript 5, simplemente ven una declaración de expresión sin efectos secundarios. Se espera que las futuras versiones de los estándares ECMAScript se introduzcan usecomo una palabra clave real; las citas se volverían obsoletas.
  • use strictsolo se puede usar al comienzo de un script o de una función, es decir, debe preceder a cualquier otra declaración (real). No tiene que ser la primera instrucción en un script de función: puede estar precedido por otras expresiones de declaración que consisten en literales de cadena (y las implementaciones de JavaScript pueden tratarlas como directivas específicas de implementación). Las declaraciones de literales de cadena, que siguen a una primera declaración real (en un script o función) son declaraciones de expresión simple. Los intérpretes no deben interpretarlos como directivas y no tienen ningún efecto.

La use strictdirectiva indica que el siguiente código (en un script o una función) es un código estricto. El código en el nivel más alto de un script (código que no está en una función) se considera código estricto cuando el script contiene una use strictdirectiva. El contenido de una función se considera código estricto cuando la función en sí misma se define en un código estricto o cuando la función contiene una use strictdirectiva. El código que se pasa a un eval()método se considera código estricto cuando eval()se llamó desde un código estricto o contiene la use strictpropia directiva.

El modo estricto de ECMAScript 5 es un subconjunto restringido del lenguaje JavaScript, que elimina los déficits relevantes del lenguaje y presenta una verificación de errores más estricta y una mayor seguridad. A continuación se enumeran las diferencias entre el modo estricto y el modo normal (de los cuales los tres primeros son particularmente importantes):

  • No puede usar la withdeclaración en modo estricto.
  • En modo estricto, todas las variables deben declararse: si asigna un valor a un identificador que no se ha declarado como variable, función, parámetro de función, parámetro de cláusula catch o propiedad del global Object, obtendrá un ReferenceError. En modo normal, el identificador se declara implícitamente como una variable global (como una propiedad de la global Object)
  • En modo estricto, la palabra clave thistiene el valor undefineden funciones que se invocaron como funciones (no como métodos). (En modo normal thissiempre apunta al global Object). Esta diferencia se puede usar para probar si una implementación admite el modo estricto:
var hasStrictMode = (function() { "use strict"; return this===undefined }());
  • También cuando se invoca una función con call()o applyen modo estricto, entonces thises exactamente el valor del primer argumento de la call()o apply()invocación. (En modo normal nully undefinedse reemplazan por los Objectvalores globales y, que no son objetos, se convierten en objetos).

  • En modo estricto, obtendrá un TypeError, cuando intente asignar propiedades de solo lectura o definir nuevas propiedades para un objeto no extensible. (En modo normal, ambos simplemente fallan sin mensaje de error).

  • En modo estricto, al pasar código a eval(), no puede declarar o definir variables o funciones en el ámbito de la persona que llama (como puede hacerlo en modo normal). En cambio, se crea un nuevo alcance eval()y las variables y funciones están dentro de ese alcance. Ese alcance se destruye después de que eval()finaliza la ejecución.
  • En modo estricto, el objeto-argumento de una función contiene una copia estática de los valores, que se pasan a esa función. En modo normal, el objeto-argumentos tiene un comportamiento algo "mágico": los elementos de la matriz y los parámetros de la función nombrada hacen referencia al mismo valor.
  • En modo estricto, obtendrá un mensaje SyntaxErrorcuando el deleteoperador sea seguido por un identificador no calificado (una variable, función o parámetro de función). En modo normal, la deleteexpresión no haría nada y se evalúa como false.
  • En modo estricto, recibirá un TypeErrormensaje cuando intente eliminar una propiedad no configurable. (En modo normal, el intento simplemente falla y deletese evalúa la expresión false).
  • En modo estricto, se considera un error sintáctico cuando intenta definir varias propiedades con el mismo nombre para un objeto literal. (En modo normal no hay error).
  • En modo estricto, se considera un error sintáctico cuando una declaración de función tiene múltiples parámetros con el mismo nombre. (En modo normal no hay error).
  • En modo estricto, los literales octales no están permitidos (estos son literales que comienzan con 0x. (En modo normal, algunas implementaciones permiten literales octales).
  • En modo estricto los identificadores evaly argumentsse tratan como palabras clave. No puede cambiar su valor, no puede asignarles un valor y no puede usarlos como nombres para variables, funciones, parámetros de función o identificadores de un bloque catch.
  • En modo estricto hay más restricciones sobre las posibilidades de examinar la pila de llamadas. arguments.callery arguments.calleecausa un TypeErroren una función en modo estricto. Además, algunas propiedades de llamadas y argumentos de las funciones en modo estricto provocan un TypeErrorcuando intentas leerlas.
Ely
fuente
44
"En modo estricto, los literales octales no están permitidos (estos son literales que comienzan con 0x ...)" los literales octales comienzan con un encabezado 0.
Alex Gittemeier
83

Mis dos centavos:

Uno de los objetivos del modo estricto es permitir una depuración más rápida de los problemas. Ayuda a los desarrolladores lanzando excepciones cuando ocurren ciertas cosas incorrectas que pueden causar un comportamiento silencioso y extraño de su página web. En el momento en que lo usemos use strict, el código arrojará errores que ayudarán al desarrollador a solucionarlo por adelantado.

Algunas cosas importantes que he aprendido después de usar use strict:

Impide la declaración de variable global:

var tree1Data = { name: 'Banana Tree',age: 100,leafCount: 100000};

function Tree(typeOfTree) {
    var age;
    var leafCount;

    age = typeOfTree.age;
    leafCount = typeOfTree.leafCount;
    nameoftree = typeOfTree.name;
};

var tree1 = new Tree(tree1Data);
console.log(window);

Ahora, este código crea nameoftreeun alcance global al que se puede acceder usando window.nameoftree. Cuando implementamosuse strict el código arrojaríamos un error.

Error de referencia no capturado: nameoftree no está definido

Sample

Elimina la withdeclaración:

withlas declaraciones no se pueden minimizar usando herramientas como uglify-js . También están en desuso y se eliminan de futuras versiones de JavaScript.

Sample

Previene duplicados:

Cuando tenemos propiedad duplicada, arroja una excepción

SyntaxError no capturado: la propiedad de datos duplicados en el objeto literal no está permitida en modo estricto

"use strict";
var tree1Data = {
    name: 'Banana Tree',
    age: 100,
    leafCount: 100000,
    name:'Banana Tree'
};

Hay pocos más, pero necesito obtener más conocimiento sobre eso.

Shubh
fuente
¡Con ECMAScript 2015, los nombres duplicados de propiedades se permiten nuevamente! Ver documentación de MDN .
philmcole
62

Si usa un navegador lanzado en el último año más o menos, entonces probablemente sea compatible con el modo JavaScript Strict. Solo los navegadores anteriores antes de que ECMAScript 5 se convirtiera en el estándar actual no lo admiten.

Las comillas alrededor del comando aseguran que el código seguirá funcionando también en los navegadores más antiguos (aunque las cosas que generan un error de sintaxis en modo estricto generalmente solo harán que el script funcione mal de alguna manera difícil de detectar en esos navegadores más antiguos).

Stephen
fuente
12
Entonces que hace?
Anish Gupta
77
... esto describe en parte la compatibilidad, pero no lo que realmente hace.
courtimas
58

Al agregar "use strict";, los siguientes casos arrojarán un SyntaxError antes de que se ejecute el script:

  • Allanando el camino para futuras versiones de ECMAScript , utilizando una de las palabras clave recién reservados (en previsión de ECMAScript 6 ): implements, interface, let, package, private, protected, public, static, y yield.

  • Declarando función en bloques

    if(a<b){ function f(){} }
  • Sintaxis octal

    var n = 023;
  • this señalar al objeto global.

     function f() {
          "use strict";
          this.a = 1;
     };
     f(); 
  • Declarar dos veces el mismo nombre para un nombre de propiedad en un objeto literal

     {a: 1, b: 3, a: 7} 

    Este ya no es el caso en ECMAScript 6 ( error 1041128 ).

  • Declarando dos argumentos de función con la misma función de nombre

    f(a, b, b){}
  • Establecer un valor en una variable no declarada

    function f(x){
       "use strict";
       var a = 12;
       b = a + x*35; // error!
    }
    f();
  • Usar deleteen un nombre variabledelete myVariable;

  • Usando evalo argumentscomo variable o nombre de argumento de función

    "use strict";
    arguments++;
    var obj = { set p(arguments) { } };
    try { } catch (arguments) { }
    function arguments() { } 

Fuentes:

zangw
fuente
¡Con ECMAScript 2015, los nombres duplicados de propiedades se permiten nuevamente! Ver documentación de MDN .
philmcole
53

El modo estricto realiza varios cambios en la semántica de JavaScript normal:

  • elimina algunos errores silenciosos de JavaScript cambiándolos para arrojar errores.

  • corrige errores que dificultan que los motores de JavaScript realicen optimizaciones.

  • prohíbe que alguna sintaxis se defina en futuras versiones de ECMAScript.

para más información vistit Strict Mode- Javascript

Renganathan MG
fuente
52

"Usar estricto"; es un seguro que el programador no usará las propiedades sueltas o malas de JavaScript. Es una guía, al igual que una regla te ayudará a hacer líneas rectas. "Usar estricto" lo ayudará a hacer "codificación directa".

Aquellos que prefieren no usar reglas para hacer sus líneas rectas generalmente terminan en esas páginas pidiendo que otros depuren su código.

Créame. La sobrecarga es insignificante en comparación con el código mal diseñado. Doug Crockford, quien ha sido desarrollador senior de JavaScript durante varios años, tiene una publicación muy interesante aquí . Personalmente, me gusta volver a su sitio todo el tiempo para asegurarme de no olvidar mi buena práctica.

La práctica moderna de JavaScript siempre debe evocar el "Uso estricto"; pragma La única razón por la que el Grupo ECMA ha hecho que el modo "Estricto" sea opcional es permitir que los codificadores con menos experiencia tengan acceso a JavaScript y darles tiempo para adaptarse a las nuevas y más seguras prácticas de codificación.

usuario2436758
fuente
66
La razón por la cual el modo estricto es opcional no tiene nada que ver con lo que has dicho. La verdadera razón es no romper el código existente que puede no conformarse .
Dexygen
17
De hecho, los codificadores menos experimentados deberían ser los primeros en permitir el "uso estricto";
Antti Haapala
46

Incluir use stricten el comienzo de todos sus archivos JavaScript sensibles desde este punto es una pequeña forma de ser un mejor programador de JavaScript y evitar que las variables aleatorias se vuelvan globales y las cosas cambien en silencio.

Marcador de posición
fuente
42

Citando de w3schools :

La directiva de "uso estricto"

La directiva "use estricto" es nueva en JavaScript 1.8.5 (versión 5 de ECMAScript).

No es una declaración, sino una expresión literal, ignorada por versiones anteriores de JavaScript.

El propósito de "usar estricto" es indicar que el código debe ejecutarse en "modo estricto".

Con el modo estricto, no puede, por ejemplo, usar variables no declaradas.

¿Por qué modo estricto?

El modo estricto facilita la escritura de JavaScript "seguro".

El modo estricto cambia la "sintaxis incorrecta" previamente aceptada en errores reales.

Como ejemplo, en JavaScript normal, escribir mal un nombre de variable crea una nueva variable global. En modo estricto, esto arrojará un error, haciendo imposible crear accidentalmente una variable global.

En JavaScript normal, un desarrollador no recibirá ningún comentario de error al asignar valores a propiedades no editables.

En el modo estricto, cualquier asignación a una propiedad no editable, una propiedad de obtención, una propiedad no existente, una variable no existente o un objeto no existente arrojará un error.

Consulte http://www.w3schools.com/js/js_strict.asp para saber más

Heich-B
fuente
37

"use strict"hace que el código JavaScript se ejecute en modo estricto , lo que básicamente significa que todo debe definirse antes de su uso. La razón principal para usar el modo estricto es evitar usos globales accidentales de métodos indefinidos.

También en modo estricto, las cosas se ejecutan más rápido, algunas advertencias o advertencias silenciosas arrojan errores fatales, es mejor usarlo siempre para hacer un código más ordenado.

"use strict"es muy necesario para ser utilizado en ECMA5, en ECMA6 es parte de JavaScript por defecto , por lo que no es necesario agregarlo si está utilizando ES6.

Mire estas declaraciones y ejemplos de MDN:

La directiva de "uso estricto"
"uso estricto" La directiva de "uso estricto" es nueva en JavaScript 1.8.5 (versión 5 de ECMAScript). No es una declaración, sino una expresión literal, ignorada por versiones anteriores de JavaScript. El propósito de "usar estricto" es indicar que el código debe ejecutarse en "modo estricto". Con el modo estricto, no puede, por ejemplo, usar variables no declaradas.

Ejemplos de uso del "uso estricto":
Modo estricto para funciones: del mismo modo, para invocar el modo estricto para una función, coloque la instrucción exacta "uso estricto"; (o 'use estricto';) en el cuerpo de la función antes de cualquier otra declaración.

1) modo estricto en funciones

 function strict() {
     // Function-level strict mode syntax
     'use strict';
     function nested() { return 'And so am I!'; }
     return "Hi!  I'm a strict mode function!  " + nested();
 }
 function notStrict() { return "I'm not strict."; }

 console.log(strict(), notStrict());

2) modo estricto de script completo

'use strict';
var v = "Hi! I'm a strict mode script!";
console.log(v);

3) Asignación a un global no grabable

'use strict';

// Assignment to a non-writable global
var undefined = 5; // throws a TypeError
var Infinity = 5; // throws a TypeError

// Assignment to a non-writable property
var obj1 = {};
Object.defineProperty(obj1, 'x', { value: 42, writable: false });
obj1.x = 9; // throws a TypeError

// Assignment to a getter-only property
var obj2 = { get x() { return 17; } };
obj2.x = 5; // throws a TypeError

// Assignment to a new property on a non-extensible object.
var fixed = {};
Object.preventExtensions(fixed);
fixed.newProp = 'ohai'; // throws a TypeError

Puedes leer más sobre MDN .

Alireza
fuente
31

Hay una buena charla de algunas personas que estaban en el comité ECMAScript: Cambios a JavaScript, Parte 1: ECMAScript 5 " sobre cómo el uso incremental de"use strict" interruptor permite a los implementadores de JavaScript limpiar muchas de las características peligrosas de JavaScript sin romper repentinamente cada sitio web en el mundo.

Por supuesto, también habla sobre cuáles son muchas de esas características erróneas y cómo ECMAScript 5 las soluciona.

FutureNerd
fuente
27

Pequeños ejemplos para comparar:

Modo no estricto:

for (i of [1,2,3]) console.log(i)
    
// output:
// 1
// 2
// 3

Modo estricto:

'use strict';
for (i of [1,2,3]) console.log(i)

// output:
// Uncaught ReferenceError: i is not defined

Modo no estricto:

String.prototype.test = function () {
  console.log(typeof this === 'string');
};

'a'.test();

// output
// false

String.prototype.test = function () {
  'use strict';
  
  console.log(typeof this === 'string');
};

'a'.test();

// output
// true

Bronceado
fuente
2
Tenga en cuenta que el código anterior agregará la variable i al alcance global (generalmente, esta no es una práctica recomendada y el modo estricto ayuda a evitar eso).
michael
1
¿Alguien puede explicar el segundo ejemplo? No lo entiendo ¿No debería this === 'a'en ambos ejemplos?
MaximeW
19

Tenga en cuenta que use strictse introdujo en EcmaScript 5 y se mantuvo desde entonces.

A continuación se detallan las condiciones para activar el modo estricto en ES6 y ES7 :

  • El código global es un código de modo estricto si comienza con un Prólogo de directiva que contiene una Directiva de uso estricto (consulte 14.1.1).
  • El código del módulo es siempre un código de modo estricto.
  • Todas las partes de una declaración de clase o una expresión de clase son códigos de modo estrictos.
  • El código de evaluación es un código de modo estricto si comienza con un Prólogo de directiva que contiene una Directiva de uso estricto o si la llamada a evaluación es una evaluación directa (consulte 12.3.4.1) que está contenida en un código de modo estricto.
  • El código de función es un código de modo estricto si la Declaración de función, Expresión de función, Declaración de generador, Expresión de generador, Definición de método o Flechafunción asociada está contenida en el código de modo estricto o si el código que produce el valor del intervalo interno [[ECMAScriptCode]] de la función comienza con un Prólogo directivo que contiene una Directiva de uso estricto.
  • El código de función que se proporciona como argumentos para los constructores de función y generador incorporados es un código de modo estricto si el último argumento es una Cadena que cuando se procesa es un FunctionBody que comienza con un Prólogo de directiva que contiene una Directiva de uso estricto.
Oriol
fuente
14

Las razones principales por las que los desarrolladores deberían usar "use strict"son:

  1. Evita la declaración accidental de variables globales. El uso "use strict()"se asegurará de que las variables se declaren varantes de su uso. P.ej:

    function useStrictDemo(){
     'use strict';
     //works fine
     var a = 'No Problem';
    
     //does not work fine and throws error
     k = "problem"
    
     //even this will throw error
     someObject = {'problem': 'lot of problem'};
    }
  2. NB: la "use strict"directiva solo se reconoce al comienzo de un script o una función.
  3. La cadena "arguments"no se puede usar como una variable:

    "use strict";
    var arguments = 3.14;    // This will cause an error
  4. Restringirá los usos de palabras clave como variables. Intentar usarlos arrojará errores.

En resumen, su código será menos propenso a errores y, a su vez, le hará escribir un buen código.

Para leer más al respecto, puede consultar aquí .

Pritam Banerjee
fuente
12

"uso estricto"; es el esfuerzo de ECMA para hacer que JavaScript sea un poco más robusto. Trae a JS un intento de hacerlo al menos un poco "estricto" (otros idiomas implementan reglas estrictas desde los años 90). En realidad, "obliga" a los desarrolladores de JavaScript a seguir algún tipo de mejores prácticas de codificación. Aún así, JavaScript es muy frágil. No existen variables tipeadas, métodos tipeados, etc. Recomiendo a los desarrolladores de JavaScript que aprendan un lenguaje más robusto como Java o ActionScript3 e implementen las mismas mejores prácticas en su código JavaScript, funcionará mejor y será más fácil de usar. depurar.

PippoApps.com
fuente
12

El modo "estricto" de JavaScript se introdujo en ECMAScript 5.

(function() {
  "use strict";
  your code...
})();

Escribir "use strict";en la parte superior de su archivo JS activa la comprobación estricta de sintaxis. Realiza las siguientes tareas para nosotros:

  1. muestra un error si intenta asignar a una variable no declarada

  2. evita que sobrescriba las bibliotecas clave del sistema JS

  3. prohíbe algunas características de lenguaje inseguras o propensas a errores

use strictTambién funciona dentro de las funciones individuales. Siempre es una mejor práctica incluir use stricten su código.

Problema de compatibilidad del navegador: las directivas de "uso" están destinadas a ser compatibles con versiones anteriores. Los navegadores que no los admitan solo verán un literal de cadena que ya no se hace referencia. Entonces, lo pasarán por alto y seguirán adelante.

Rabin Pantha
fuente
12

use strictes una forma de hacer que su código sea más seguro, porque no puede usar características peligrosas que pueden funcionar de la manera no esperada. Y, como se escribió anteriormente, hace que el código sea más estricto.

Просто программист
fuente
11

Use Strict se usa para mostrar errores comunes y repetidos para que se maneje de manera diferente y cambie la forma en que se ejecuta el script java, tales cambios son:

  • Previene globals accidentales

  • Sin duplicados

  • Elimina con

  • Elimina esta coerción.

  • Eval más seguro ()

  • Errores para inmutables

también puedes leer este artículo para más detalles

Wesam
fuente
11

Normalmente, JavaScript no sigue reglas estrictas, por lo tanto, aumenta las posibilidades de errores. Después de usar "use strict", el código JavaScript debe seguir un conjunto estricto de reglas como en otros lenguajes de programación, como el uso de terminadores, declaración antes de la inicialización, etc.

Si "use strict"se usa, el código debe escribirse siguiendo un estricto conjunto de reglas, lo que disminuye las posibilidades de errores y ambigüedades.

Bikash Chapagain
fuente
7

"uso estricto"; Define que el código JavaScript debe ejecutarse en "modo estricto".

  • La directiva de "uso estricto" era nueva en ECMAScript versión 5.
  • No es una declaración, sino una expresión literal, ignorada por versiones anteriores de JavaScript.
  • El propósito de "usar estricto" es indicar que el código debe ejecutarse en "modo estricto".
  • Con el modo estricto, no puede, por ejemplo, usar variables no declaradas.

Todos los navegadores modernos admiten "uso estricto", excepto Internet Explorer 9 y versiones inferiores .

Desventaja

Si un desarrollador usa una biblioteca que estaba en modo estricto, pero el desarrollador estaba acostumbrado a trabajar en modo normal, podría llamar a algunas acciones en la biblioteca que no funcionarían como se esperaba.

Peor aún, dado que el desarrollador está en modo normal, no tienen las ventajas de que se generen errores adicionales, por lo que el error puede fallar en silencio.

Además, como se mencionó anteriormente, el modo estricto le impide hacer ciertas cosas.

La gente generalmente piensa que no debes usar esas cosas en primer lugar, pero a algunos desarrolladores no les gusta la restricción y quieren usar todas las características del lenguaje.

Ashish
fuente
4

El modo estricto puede evitar pérdidas de memoria.

Compruebe la función a continuación escrita en modo no estricto:

function getname(){
    name = "Stack Overflow"; // Not using var keyword
    return name;
}
getname();
console.log(name); // Stack Overflow

En esta función, estamos usando una variable llamada name dentro de la función. Internamente, el compilador primero verificará si hay alguna variable declarada con ese nombre en particular en ese ámbito de función en particular. Como el compilador entendió que no existe tal variable, verificará en el ámbito externo. En nuestro caso, es el alcance global. Nuevamente, el compilador entendió que tampoco hay una variable declarada en el espacio global con ese nombre, por lo que crea una variable para nosotros en el espacio global. Conceptualmente, esta variable se creará en el ámbito global y estará disponible en toda la aplicación.

Otro escenario es que, digamos, la variable se declara en una función secundaria. En ese caso, el compilador verifica la validez de esa variable en el ámbito externo, es decir, la función padre. Solo entonces verificará el espacio global y creará una variable para nosotros allí. Eso significa que se deben hacer verificaciones adicionales. Esto afectará el rendimiento de la aplicación.


Ahora escribamos la misma función en modo estricto.

"use strict"
function getname(){
    name = "Stack Overflow"; // Not using var keyword
    return name;
}
getname();
console.log(name); 

Obtendremos el siguiente error.

Uncaught ReferenceError: name is not defined
at getname (<anonymous>:3:15)
at <anonymous>:6:5

Aquí, el compilador arroja el error de referencia. En modo estricto, el compilador no nos permite usar la variable sin declararla. Por lo tanto, se pueden evitar las pérdidas de memoria. Además, podemos escribir código más optimizado.

Jerin K Alexander
fuente