javascript- Uncaught SyntaxError: Identifier * has already been declared

Posted

技术标签:

【中文标题】javascript- Uncaught SyntaxError: Identifier * has already been declared【英文标题】: 【发布时间】:2018-09-21 07:42:10 【问题描述】:
console.log(a) //output:ƒ a()
var a = 1;
function a();
var a = 10;
console.log(a) //output:10

=====================

var a = 1;
if(true)
  function a();
  var a = 10;

console.log(a) // this code throws Uncaught SyntaxError: Identifier 'a' has already been declared

上面的代码 sn-ps 都是相同的,除了 if 块。为什么后者在 javascript 中允许在同一范围内使用 var 两次删除相同变量时抛出错误,如下所示

 function a();
 var a = 10; //no error

对于在上述代码中从 `var a = 10 中删除 var 后的稍微不同的场景,它工作正常但输出令人惊讶

 var a = 1;
 if(true) 
   function a();
   a = 10;
 
 console.log(a) //output:ƒ a()

我很惊讶看到这个输出,因为我期待 10 ..因为在 if 块中声明的两个变量引用上面声明的相同变量,因为 javascript var 不尊重块范围但函数范围......所以为什么不输出以上应该是10? 其中,当用函数表达式替换函数定义时,下面的代码输出 10。

  var a = 1;
  if(true) 
    var a = function() console.log() 
    a = 10;
  
  console.log(a) //output:10

【问题讨论】:

好吧,if 块中的函数声明在 ES5 中是无效的,因此使用它们将有 ES6 semantics 对重复声明有更严格的规则。 相关,如果不重复:Why does redeclaring a function identifier within a try block throw a SyntaxError? 【参考方案1】:

这令人惊讶,因为 javascript var 不尊重块作用域而是函数作用域......

当然,但是您没有使用 var 在块范围内声明 a。你使用了一个函数声明,它是 does respect block scopes(否则它将是 completely invalid code,就像在 ES5 严格模式下一样)。

在 javascript 中允许使用 var 在同一范围内两次声明同一个变量,如下所示

这里同样适用。块中的 function 声明使用 ES6 声明语义(如 letconst),不允许重新声明。

【讨论】:

【参考方案2】:

案例 1

console.log(a) //output:ƒ a()
var a = 1;
function a();
var a = 10;
console.log(a) //output:10

将呈现为

var a;
a = function(); // now a holds the value as a function
console.log(a); // output : f a()
a = 1; // a is a var that holds value 1
a = 10; // a is a var that holds value 10
console.log(a); // output : 10

案例 2

var a = 1;
if(true)
   function a();
   var a = 10;

console.log(a)

将呈现为

var a;
a = 1;
if(true) 
    a = function() ;
    let a; // The function declaration in the block uses ES6 declaration semantics (like let or const), which does not allow re-declarations.
    var a; // throws Uncaught SyntaxError: Identifier 'a' has already been declared
    a = 10;

console.log(a);

案例 3

var a = 1;
if(true)
    function a();
    a = 10;
 
console.log(a)

将呈现为

var a;
a = 1;
if(true) 
    a = function() ;
    let a;
    a = 10;

console.log(a); // output : f a()

案例 4

var a = 1;
if(true)
    var a= function()console.log()
    a = 10;

console.log(a)

将呈现为

var a;
a = 1;
if(true) 
    a = function()console.log()
    a = 10;

console.log(a) // output:10

案例 5

var a = 1;
if(true)
    function a();
    a = 10;
    console.log(a) 

console.log(a) 

将呈现为

var a;
a = 1;
if(true)
    a = function() ;
    let a;
    a = 10;
    console.log(a); // output:10

console.log(a); // output : f a()

【讨论】:

在案例 3 中更像 let a @Bergi - 谢谢。我在发表我的理解时参考了您的回答。希望你没事。如果没有,我很乐意删除我的答案。 @PrashantTapase - 谢谢。为了更好地理解,我更新了我的答案,您现在也可以看到错误陈述的行为。 @nikhilagw 没关系 :-) 现在很清楚了。非常感谢nikhilagw。谢谢@Bergi【参考方案3】:

解决这个问题的简单方法是使用 IIFE

(function() 
var sahil = 
  checkThis: function() 
    console.log(this);

    function checkOther() 
      console.log(this);
    
    checkOther(); // checkThis() function called in "global context", will
                  // return "this" as "window"
  
;
var moo = sahil.checkThis;
moo(); // moo() function called in "global context", will return "this" as "window" )();

【讨论】:

以上是关于javascript- Uncaught SyntaxError: Identifier * has already been declared的主要内容,如果未能解决你的问题,请参考以下文章

Uncaught Error: Bootstrap's JavaScript requires jQuery

Javascript Uncaught TypeError:AccountID不是一个函数

Uncaught Error: Bootstrap's JavaScript requires jQuery

JavaScript报错Uncaught SyntaxError: Invalid shorthand property initializer

javascript Uncaught TypeError:无法读取null的属性'firstChild'[重复]

javascript- Uncaught SyntaxError: Identifier * has already been declared