Javascript奇怪的StackOverflow错误

时间:2012-07-25 00:34:29

标签: javascript error-handling stack stack-overflow

我想知道Javascript中括号的工作原因,所以我编写了这段代码进行测试:

((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((
4+4
))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))

其中包括:

( x1174
4+4
) x1174

我在Google Chrome 20(Win64)上测试了上面的代码,它给了我正确的答案(8)。

但是如果我尝试使用相同的代码,但是使用了1175个括号(两边都有),我会收到 stackoverflow 错误。

您可以在JSFiddle中查看此代码(注意:在JSFiddle中它停止使用1178个括号)

所以,我的问题是:

  • 为什么会这样?
  • 为什么它在JSFiddle上停止使用1178个括号,但在我的空白页面上只有1175个?
  • 此错误是否取决于page / browser / os?

2 个答案:

答案 0 :(得分:6)

语言通常是根据名为递归下降的模式设计的代码解析的。我不确定这是否是这种情况,但肯定是“堆栈溢出”错误是一个很大的证据。

我们的想法是,要解析表达式,您可以通过查看表达式的内容来处理语法。 带括号的表达式就像是“表达式中的表达式”。因此,对于解析器系统地解析它在第一次看到的代码中的某些表达式(对于解析器来说,它是它的永恒命运),左括号表示“确定 - 保持你正在做的事情(在堆栈上) ),从表达式可能的开头开始,解析一个新的,完整的表达式,当你看到匹配的关闭paren时回来。

因此,一千个或更多个括号的字符串触发同一活动的等效级联:把我们所拥有的东西放在架子上;潜入并获得一个子表达式,然后在我们知道它的样子时恢复。

现在这不是解析某些东西的唯一方法,应该注意。有很多方法。我个人非常喜欢递归下降解析,但没有什么特别之处(除了我认为有一天我会看到一个真正的独角兽)。

答案 1 :(得分:5)

不同浏览器的行为不同,因为它们具有不同的Javascript实现。该语言没有指定这样的事情应该如何失败,因此每个实现都以不同的方式失败。

JSFiddle与您的空白页面之间的区别是因为JSFiddle本身使用一些堆栈帧来建立运行代码的环境。