JavaScript的声明提前

本文详细解析了JavaScript中的变量作用域概念,包括全局变量和局部变量的区别,并通过实例展示了JavaScript特有的变量声明提前特性及其对程序逻辑的影响。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

JavaScript的声明提前:JavaScript函数里声明的所有变量都被“提前”至函数体的顶部。

在看例子之前我们先说一下变量的作用域:

全局变量作用域:在JavaScript代码的任何地方都可以用。

局部变量作用域:局部变量是在函数内部声明的,只在函数内部可以用。

在函数体内部,局部变量的优先级高于同名的全局变量。如果在函数内声明的一个局部变量或者函数参数中带有的变量和全局变量重名,全局变量就被局部变量遮盖。

意思是在函数中先找这个变量在函数中有没有定义,如果有定义,则用的是函数中定义的局部变量,若没有在函数中找到,则在全局里找。

此时我们看例子:

<html>
<head>
</head>
 <body>
</body>
</html>
<script>
	var scope="global";
		function f(){
			
			alert(scope);//undefined
			var scope="local";
		       alert(scope);//loacl
			}
			f();
</script>

学过java语言的同学可能会认为第一个alert(scope);的结果是“global”,但是运行上段的代码,第一个alert(scope);的结果却是undefined,这是为什么呢?

我们在f()方法里找scope变量是不是在函数体中定义过的,在函数体中找到了,但是下面一行才对scope局部变量赋值,这里会输出undefined,

是相当于在f()函数体的开始就将f()函数里声明的所有变量都被“提前”至函数体的顶部,即在开始时先var scope;了。

上面的代码相当于:

<html>
<head>
</head>
 <body>
</body>
</html>
<script>
	var scope="global";
		function f(){
			var scope;
			alert(scope);//undefined
			scope="local";
		       alert(scope);//loacl
			}
			f();
			
			
</script>

JavaScript的声明提前导致了JavaScript的函数的作用域与java语言的作用域的不同。

学过Java的同学知道在一个方法里写一个for循环,for循环里定义的变量只能在for循环里使用,出了for循环,就不能用了。
但是JavaScript的函数的作用域指的是:在函数体内声明的所有变量在函数体内始终是可见的。不管这个变量是在函数的什么时候地方声明的。

看下面的例子:


<html>
<head>
</head>
 <body>
</body>
</html>
<script>
	 function test(o){
	 		var i=0;
	 		if(typeof(o) == "object"){
	 			 var j=2;
	 			 for(var k=0;k<10;k++){
	 			 	
	 			 	alert("["+k+"]"+k);
	 			 	alert("j---"+j);//2
	 			 	}
	 			alert("---"+k);//10
	 			
	 			}
	 		alert("===="+j);//2
	 	}
	 	var n=new Number(3);
	 	test(n);
</script>
运行后,alert("["+k+"]"+k);的k输出0-9的值,    alert("j---"+j);的j的值是2,

alert("---"+k);的k是10,上面的 “JavaScript的函数声明提前” 理解的话,就知道了:在函数里声明的变量都被提前到函数体的开头声明了。

alert("===="+j);的j是2,和上面的解释一样。

这个例子相当于:

<html>
<head>
</head>
 <body>
</body>
</html>
<script>
	 function test(o){
	 		var i=0;
	 		 var j;
	 		 var k;
	 		if(typeof(o) == "object"){
	 			 j=2;
	 			 for(k=0;k<10;k++){
	 			 	
	 			 	alert("["+k+"]"+k);
	 			 	alert("j---"+j);
	 			 	}
	 			alert("---"+k);//10
	 			
	 			}
	 		alert("===="+j);//2
	 	}
	 	var n=new Number(3);
	 	test(n);
</script>
test(o)函数中有个if判断,因此,如果是下面的情况呢:

<html>
<head>
</head>
 <body>
</body>
</html>
<script>
	 function test(o){
	 		var i=0;
	 		if(typeof(o) == "object"){
	 			 var j=2;
	 			 for(var k=0;k<10;k++){
	 			 	
	 			 	alert("["+k+"]"+k);
	 			 	
	 			 	}
	 			alert("---"+k);
	 			
	 			}
	 		alert("===="+j);//undefined
	 	}
	 	
	 	test(3);
</script>
此时if()里面的不会执行,就直接alert("===="+j);,结果j是undefined。因为JavaScript的声明提前原因,所以这里在开头相当定义了var  j;但是后面没有给j初始化,所以alert("===="+j);,结果j是undefined。


### JavaScript声明函数的方法 #### 函数声明 函数声明是一种通过 `function` 关键字来定义命名函数的方式。这种方式允许函数在被调用之前存在于代码中,因为它们会被解析器提前处理。 ```javascript function addNumbers(a, b) { return a + b; } ``` 这种形式的函数会在整个作用域内可用,即使是在其实际定义位置之前的代码部分也能正常工作[^1]。 #### 函数表达式 当使用函数表达式时,函数通常会作为一个值分配给变量或其他实体。这使得函数可以在之后才变得可访问,并且不会像函数声明那样经历所谓的“函数提升”。 ```javascript const multiplyNumbers = function(x, y) { return x * y; }; ``` 此类型的函数只有在其赋值语句被执行过后才能被调用[^4]。 #### 对象方法 对象内部也可以包含作为属性存在的函数,这些被称为对象的方法。可以通过点符号或方括号语法来调用这类成员函数。 ```javascript const person = { name: "Alice", sayHello: function() { console.log(`Hello from ${this.name}`); } }; person.sayHello(); ``` 这里展示了如何在一个对象里设置一个名为 `sayHello` 的方法并对其进行调用[^3]。 #### 箭头函数 自 ES6 起引入了箭头函数,这是一种更为简洁的方式来创建匿名函数。它不仅减少了所需的代码量,还改变了上下文中的 `this` 值绑定行为。 ```javascript const squareNumber = num => num * num; console.log(squareNumber(5)); // 输出 25 ``` 对于单个参数的情况,可以省略圆括号;如果主体只有一条返回语句,则大括号和显式的 `return` 可以简化掉[^2]。 #### IIFE(立即执行函数表达式) IIFEs 是指那些一旦定义就会马上自动运行的一次性使用的函数。这对于创建局部范围内的私有变量非常有用。 ```javascript (function immediate() { console.log('This will run as soon as it is defined'); })(); ``` 注意这里的额外一对圆括号包裹着整个函数体加上后面的空括号用于触发执行。
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值