为什么[eval]在[eval] [0]('code')中工作?

时间:2013-10-22 06:06:59

标签: javascript

我看到这种方式执行代码:

[eval][0]('alert("hello")')  

我想知道方括号包围的不带引号的'eval'意味着什么,以及为什么这样做。 (例如,window['eval'][0]('alert("hello")')将导致TypeError)。有没有描述这种语法的教程?

4 个答案:

答案 0 :(得分:6)

这是indirect eval call

引用文章:

  

根据ES5,所有这些都是间接调用,应该执行   全球范围内的代码

因此,您可以使用这些“技巧”在全局范围内执行eval而不是当前范围。

它在[eval]之前是一个数组,其第0个元素是eval函数,即[eval][0] === eval,并且您正在调用它传递字符串'alert("hello")'作为论点。

答案 1 :(得分:2)

括号括起来的不带引号的eval是一个包含一个eval元素的数组。

[eval][0]('alert("hello")')

表示获取数组[eval]的第一个元素并将'alert("hello")'传递给它。换句话说,

eval('alert("hello")')


window['eval'][0]('alert("hello")')

另一方面,

尝试获取window['eval']的第一个元素,它不是一个数组,因此也就是TypeError。 window['eval']eval相同,除非在范围内有另一个名为eval的变量。

答案 2 :(得分:2)

您的示例导致TypeError的原因:

window['eval'][0]('alert("hello")')

是因为你遗漏了一组括号,它们会使它等价:

[window['eval']][0]('alert("hello")')

您给出的初始语法构造了一个包含一个元素的数组,即函数eval。因此,此数组的第0个元素是eval函数,使用方括号立即取消引用。

答案 3 :(得分:1)

在Javascript中

[x]

是包含x的一个元素的列表。从而

[x][0]

只是一种冗长而低效的说法x

你的例子

[eval][0]('alert("hello")')
因此

就像

eval('alert("hello")')

这种欺骗通常存在于Javascript木马或病毒中,作者试图掩盖正在发生的事情。

然而,Javascript充满了特殊情况,当与eval一起使用时,代码也可能具有强制全局评估而非本地评估的含义。

function defun(s) { [eval][0](s); }
function defun2(s) { eval(s); }

defun2("function square(x){return x*x}")
---> undefined

square(12)
---> ReferenceError: square is not defined

defun("function square(x){return x*x}")
---> undefined

square(12)
---> 144

有关详细信息,请参阅Matteo Tassinari回答链接(请注意,链接文章有点过时,因此请忽略有关webkit行为的详细信息。)