2010-02-26 10 views
39

¿Qué alcance tiene el modo estricto pragma en ECMAScript5?En ECMAScript5, ¿cuál es el alcance del "uso estricto"?

"use strict"; 

me gustaría hacer esto (sobre todo porque JSLint no se queja de ello):

"use strict"; 

(function() { 
    // my stuff here... 
}()); 

Pero no estoy seguro de si eso fuera a romper otro código o no. Sé que puedo hacer esto, que se alcance el pragma a la función ...

(function() { 

    "use strict"; 

    // my stuff here... 

}()); 

pero JSLint se queja de ello (cuando la opción "estricta" JSLint está habilitada), ya que piensa que está ejecutando el código antes de habilitar "use strict".

Aquí está mi pregunta. Si tengo fileA.js:

"use strict"; 
// do some stuff 

y fileB.js:

eval(somecodesnippet); // disallowed by "use strict" 

y luego incluirlos en mi página HTML en ese mismo orden, va a ser el pragma con ámbito en el fichero, o voluntad el pragma se desborda en fileB, bloqueando así la ejecución de eval?

+0

lado A Nota: la presentación de Douglad Crockford sobre "El estado y el futuro de Javascript fue realmente genial. Habla sobre algunas de las nuevas características, como estricto al final de la charla. Aquí está el enlace: http://www.infoq.com/presentations/The-State-and-Future-of-JavaScript –

+0

'eval()' está permitido con '" use strict "', solo obtiene un alcance global. –

Respuesta

2

EDIT Parece que era incorrecto. Por favor, consulte Jeff Walden's answer below.

Salida esta respuesta a una pregunta relacionada: What does "use strict" do in JavaScript, and what is the reasoning behind it?

A pesar de las quejas de JSLint, puede (y debe ) "use strict"; utilizar dentro de una función si solo deseas que la función esté en modo estricto. Si lo usa en el contexto global, forzará que todo su código esté en modo estricto. Respuesta corta: sí, bloqueará el uso de eval.

+2

Esta respuesta es incorrecta. El uso de la directiva en la parte superior de 'fileA.js' hace que la totalidad de ese archivo esté en modo estricto, pero no hace que' fileB.js' esté en modo estricto, independientemente del orden en que se incluyan en la página HTML. . Además, 'eval()' funciona de manera diferente en modo estricto, pero aún funciona. No está "bloqueado". –

54

"use strict" se aplica solo a la función o al alcance del programa. Por lo tanto, si tiene fileA.js con "use strict" en la parte superior, fileA.js se ejecuta en modo estricto y todas las funciones definidas en él harán lo mismo cuando se le llame. Pero fileB.js es un programa separado, por lo que "use strict" de fileA.js no se aplica a él, y por lo tanto fileB.js se ejecutará en modo no estricto. (Por supuesto, si somecodesnippet comienza con una directiva "use strict" y se analiza correctamente, ese código se ejecutará en modo estricto, y las funciones definidas por ese código harán lo mismo.) La estricción no "sangra" en absoluto, y según ES5 4.2.2 (ciertamente no normativo, pero estoy seguro de que podría desenterrar una referencia normativa para esto si fuera necesario), "una implementación debe admitir la combinación de unidades de código de modo estricto y sin restricciones en un solo programa compuesto".

Esto se debe a esto: si utiliza el modo estricto en el ámbito global a veces pero no siempre, ya no puede concatenar sus scripts en un solo archivo. Supongamos que tiene los guiones A, B, C, D en ese orden. Si A es estricto, la concatenación total será estricta, ¡incluso si B/C/D no! Por el contrario, si A no es estricto (y no está vacío), la concatenación general no será estricta, incluso si B/C/D fuera estricto. Esto ya ha mordido al menos un sitio de usuarios iniciales.

Dicho todo esto, el modo estricto no prohíbe eval.Cuando se llama eval de la manera normal en modo estricto, usando la sintaxis de programa del formulario eval(code [, ...]), es una evaluación "directa" que se comporta de la manera en que eval siempre tiene - excepto que code siempre se evalúa como código de modo estricto, incluso si code doesn ' Comenzar con una directiva "use strict", y salvo que las variables creadas por el código se mantienen en su propio almacenamiento separado de las variables existentes. (La semántica exacta es un poco complicada, trabajo en el motor de JavaScript de Firefox, últimamente implementando esto, e incluso después de una buena cantidad de tiempo en la especificación y trabajando en una implementación, todavía no soy intuitivo).

Si no se llama así - eval.call(...), setTimeout(eval, ...), setInterval(eval, ...), var ev = eval; ev(...);, etc. - es una evaluación "indirecta". La evaluación indirecta (ya sea dentro o fuera del modo estricto) se comporta de forma un poco diferente: la resolución del nombre y la definición de la variable se producen como si estuvieran en el ámbito global. (El código se ejecutará código de modo tan estricto sólo si se comienza con una directiva "use strict".)

compatibilidad con el modo estricto está casi - pero no del todo - terminada en el último Firefox nightlies, por lo que puede valer la pena la descarga de uno a jugar alrededor con esas partes del modo estricto que se implementan. Todavía diría que espere el uso de producción hasta que esté completo, pero definitivamente está listo para la experimentación (siempre y cuando comprenda que el modo estricto todavía no está completo). (En cuanto al enlace de Sean McMillan, tenga en cuenta que sus afirmaciones de "soporte" representan el mínimo extremo de funcionalidad necesario para cada bala. Las pruebas de modo estrictas son mucho mejores, aunque para estar seguro de que no están en ninguna parte cerca de cubrir el modo estricto por completo.)

+4

'Estricto absolutamente no "sangra"' - Esto no es del todo correcto. No se puede usar '.caller' en un código no estricto cuando la función en la que se usa está definida en modo estricto. De modo que el código no estricto puede, de hecho, romperse debido a que otro código está en modo estricto; consideraría ese sangrado. – AndreKR

+1

La forma en que se formuló la pregunta original, interpretaría que "sangrar" significa en el sentido del código fuente léxico y textual, de la secuencia de comandos B recogiendo rigor del guión A, sin que B opte por la estrictez. Obviamente, los efectos de un guión (incluidos los causados ​​por el rigor) son visibles, "sangrar", podría decirse, en otros guiones.La * naturaleza * del efecto puede variar según el rigor del guión de activación. Pero estricto o no, los efectos de un guión son visibles en el otro. Eso no parece una definición particularmente útil de "sangrado" para mí. –

0
eval(somecodesnippet); // disallowed by "use strict" 

No si declara algún codigo antes.

var somecodesnippet = "su impresionante codensippet aquí";

eval (somecodesnippet); // NO anulado por "utilizar estricta"

0

El archivo completo:

<script...> 
    "use strict"; 

o

La función entera y sus funciones Embebido por ejemplo:

function fn(){ 
    "use strict"; 
+0

Ya hay una respuesta aceptada, que resuelve el problema de OP. El tuyo no agrega más calidad. –

Cuestiones relacionadas