参数名、变量名、函数名的优先级

【js】JavaScript中同名标识符优先级

2015年09月16日 13:31:46 阅读数:360

一,局部变量先使用后声明,不影响外部同名变量

1

2

3

4

5

6

7

var x = 1; // --> 外部变量x

function fn(){

    alert(x);  // --> undefined 局部变量x先使用

    var x = 2; // 后声明且赋值

}

fn();

alert(x); // --> 1<br>

第一点,函数fn内第一句输出x,x是在第二句才定义的。这在JS中是允许的,这里的允许是指不会出现语法错误程序可以运行。
但在其它语言如C,Java中却是不允许的。变量必须先声明后使用,如

1

2

3

4

5

6

public class Test {

    public static void main(String[] args) {

        System.out.println(x); // 先使用

        int x = 10// 后声明

    }

}

Java中编译器会提示错误,程序无法运行。


第二点,函数fn内的局部变量x不会影响到外部的变量x。即fn内alert输出不是1,而是undefined。

第三点,要是将

 alert(x);  // --> undefined 局部变量x先使用

    var x = 2; // 后声明且赋值

 

调换先后顺序则fn() 的输出结果为2.

 

二,形参优先级高于函数名

1

2

3

4

function fn(fn){

    alert(fn);

}

fn('hello'); // --> "hello"

可以看到函数名和形参同名都是fn,输出的是字符串"hello",却不是函数fn的函数体(fn.toString())。

 

三,形参优先级高于arguments

1

2

3

4

function fn(arguments){

    alert(arguments);

}

fn('hello'); // --> "hello"<br>

arguments对象可以直接在函数内使用,是语言本身提供的一个 特殊标识符 。
这里刚好将形参声明成与其同名。输出可以看到是"hello"而非"[object Object]",即形参arguments覆盖了语言本身提供的真正的arguments。

 

四,形参优先级高于只声明却未赋值的局部变量

1

2

3

4

5

function fn(a){

    var a;

    alert(a);

}

fn('hello'); // --> "hello"

函数fn形参为a,函数内第一句仅声明局部变量a,却并未赋值。从输出结果是"hello"而非undefined可以看出形参a优先级高于仅声明却未赋值的局部变量a。

 

五,声明且赋值的局部变量优先级高于形参

1

2

3

4

5

function fn(a){

    var a = 1;

    alert(a);

}

fn('hello'); // --> "1"

函数fn形参为a,函数内第一句仅声明局部变量a,赋值为1。从输出结果是"1"而非"hello"可以看出声明且赋值的局部变量a优先级高于形参a。

 

六,形参赋值给同名局部变量时

1

2

3

4

5

function fn(a){

    var a = a;

    alert(a);

}

fn('hello');

暂不运行,猜测下结果。如果按照第五点:声明且赋值的局部变量优先级高于形参。那么a将是undefined。但实际上a是"hello",即右a是形参a,左a才是局部变量a。

这里的两个a互不干扰,谁也没覆盖谁。这与刚刚说的赋值的局部变量优先级高于形参又矛盾了。但引擎这样做的确是我们想要的,因为并不希望var a = a后a是undefined。

 

 

实例:

 

 
  1. <!DOCTYPE html>

  2. <html>

  3. <body>

  4.  
  5.  
  6. <script>

  7. var num1 = 10;

  8. function test(){

  9. if(num1==10){

  10. var num1 = 1;

  11. }

  12. else{

  13. var num1 = 2;

  14. }

  15. alert(num1);

  16. }

  17. test(); //返回2

  18. </script>

  19.  
  20. </body>

  21. </html>


我一开始还没理解hoisting的时候,对这个例子百思不得其解。安装hoisting原则,var会将declaration进行hoist,但是definition并不会hoist。在var num1 = 10这句代码里面,其实包含了两个语句,第一个是declaration(也就是声明):var num1;,第二个是definition(定义赋值):num1 = 10;根据hoisting原则,声明会被hoist到当前作用域的顶端,但不会对定义hoist。因此在这个例子里面,函数test()的作用域里num1的值为undefined,不等于10,因此最后赋值为2.

  • 1
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 1
    评论
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值