【问题标题】:eval is not a function [duplicate]eval不是一个函数[重复]
【发布时间】:2017-05-22 16:04:58
【问题描述】:

这可能会让某人感兴趣并节省几个小时,这是一个令人讨厌的捆绑问题,eval 来自一个文件,而 function 来自第二个文件。

eval('console.log(0)')
(function(x){console.log(x)})(1)

将导致:Uncaught TypeError: eval(...) is not a function

这就是解决方法

eval('console.log(0)');
(function(x){console.log(x)})(1)

缺少分号,我读过几次 JS 中的分号大部分时间都是可选的。

任何 cmets 为什么 eval 在这种情况下不是一个函数?

【问题讨论】:

  • 虽然分号插入是可选的。很高兴了解 JS 引擎何时会真正插入分号。阅读此答案可能会有所帮助stackoverflow.com/questions/2846283/…
  • 这里的教训是总是在包中的文件之间放置分号:)
  • 当您将一些undefined 变量传递给eval 时,可能会发生这种情况。就我而言,我没有在 Postman 中导入一些全局变量:eval(globals.some_function)();

标签: javascript syntax eval


【解决方案1】:

JS 运行时在猜测分号应该放在哪里方面并不完美。

当它看到这个时:

eval('console.log(0)')
(function(x){console.log(x)})(1)

它错误地假定立即调用的函数表达式的结果是eval 行的一部分(一个潜在的参数将被传递给eval 求值的潜在函数)。

这是一个什么时候会起作用的例子:

eval("(function(message){ alert(message); })")
("Hi there!");

但是,在您的情况下,eval 没有对函数进行评估,因此尝试将参数传递给它会失败,因此会出现错误消息。

但是,它实际上与eval() 关系不大,尤其是。只要在 IIFE 或任何以 ( 开头的表达式之前省略分号,就会弹出此消息。

添加分号,让运行时知道 IIFE 是独立的。

规则是,您必须在后跟( 的任何行上插入分号(因为这是表达式的开头),以便将它们分开。但是,更好的规则是完全不依赖自动分号插入,始终将它们放在自己的位置。

【讨论】:

  • 这是我的猜测,但发现这是一场噩梦,因为这种代码不是手工编写的,它是许多第三方库的 concat
  • @maciejW 哦,顺便说一句,首先强烈建议不要使用eval()。它可能导致跨站点脚本攻击,速度慢并且在修改后的范围链中运行。几乎总有一种方法可以将代码重构为不需要eval()
【解决方案2】:

这是 Javascript 的 semicolon insertion 会绊倒您的少数情况之一。

这段代码:

eval('console.log(0)')
(function(x){console.log(x)})(1)

相当于这段代码:

eval('console.log(0)')(function(x){console.log(x)})(1)

换句话说,Javascript 认为表达式eval('console.log(0)') 评估为您尝试使用参数(function(x){console.log(x)}) 调用的函数。这显然不是您想要的,因此您需要在行尾使用分号。

【讨论】:

    猜你喜欢
    • 2020-10-09
    • 2021-12-13
    • 2014-02-03
    • 2021-09-29
    • 2017-11-10
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2017-12-16
    相关资源
    最近更新 更多