Javascript 为什么在try块中重新声明函数标识符会引发语法错误?

Javascript 为什么在try块中重新声明函数标识符会引发语法错误?,javascript,syntax-error,Javascript,Syntax Error,下面几行JavaScript代码 try { function _free() {} var _free = 1; } finally { } 导致以下错误: Uncaught SyntaxError: Identifier '_free' has already been declared 但是,以下两块JavaScript代码没有: 如果没有块范围,请尝试块范围: function _free() {} var _free = 1; 在功能范围内: function

下面几行JavaScript代码

try {
    function _free() {}
    var _free = 1;
} finally { }
导致以下错误:

 Uncaught SyntaxError: Identifier '_free' has already been declared
但是,以下两块JavaScript代码没有:

  • 如果没有
    块范围,请尝试
    块范围:

    function _free() {}
    var _free = 1;
    
  • 功能
    范围内:

    function a() {
        function _free() {}
        var _free = 1;
    }
    
  • 但是为什么呢

    (测试环境:Chromium 61.0.3126.0)

    因为它们是一种新的ES6功能,并且是安全的(即,在名称冲突上抛出一个错误,类似于
    let
    const
    ),但其他情况(不管是程序员错误)需要保持向后兼容并以静默方式覆盖函数。

    要进一步展开,ES5和ES6中的代码解释方式有所不同,因为添加了块作用域函数声明

    输入:

    function test() {
        try {
            function _free() { }
            var _free = 1;
        } finally { }
    }
    
    由于ES5不支持块级功能,
    \u free
    适用于父功能:

    function test() {
        var _free = function _free() { }
        try {
            var _free = 1;
        } finally { }
    }
    
    在ES6中,函数在块级别声明,语义上等于
    let
    /
    const
    声明:

    function test() {
        try {
            let _free = function _free() { }
            var _free = 1;
        } finally { }
    }
    
    这会引发一个错误,因为
    var\u free
    试图声明一个已声明的变量。 例如,ES6中也包含以下内容:

    let _free;
    var _free = 1;    // SyntaxError: Indentifier '_free' has already been declared
    
    虽然这很好:

    var _free;
    var _free = 1;    // No SyntaxError
    
    可以设置已声明标识符的值:

    let _free;
    _free = 1;
    
    因此,要将声明的标识符
    \u free
    设置为1,您需要跳过第二个声明:

    function test() {
        try {
            let _free = function _free() { }
            var _free = 1;
        } finally { }
    }
    

    我想知道这会发生在其他浏览器和旧浏览器中吗ES6@Bergi这是由于
    严格模式
    造成的。可能在什么地方用过它。我在IE中测试过它,什么也没发生。但是firefox和其他新的浏览器已经成功了it@user93前块级函数声明的处理ES6@user93IE实现了所有主流浏览器中最少的ES6功能。你在什么地方使用过
    严格模式吗?@Jai与严格模式无关,也叫
    使用严格模式:)@Mr.Alien Ahh。。。没错。我的意思是一样的。@Jai我没有:/“由于ES5不支持块级函数,_free被提升到父函数”这句话没有真正的意义。它不支持它们,所以代码只是一个语法错误。未挂起任何内容。ES6函数声明在语义上并不完全等同于
    let
    /
    const
    ,因为它仍然挂起。