今天在写js 全局变量作用域的时候,碰到了一个纳闷的问题
首先根据定义:全局变量有两种方式创建:
1 方法外部声明的变量,2 方法内部没有使用var关键字声明的变量
第一次代码
function Person(str){
this.name=str;
}
var p1=new Person('z3');
console.log(p1.name); //结果 z3
console.log(name); //结果 z3
一开始对于这两个结果,我认为是理所当然的;
第一个结果 p1.name 返回z3。首先函数内的this代表着指向当前调用者。通过Person对象创建了一个p1实例。再调用p1.name,此时的this指向就是这个对象实例。
第二个结果 name 返回 z3。 当时没有深究,认为this.name执行完之后创建的是一个全局变量(这里一下错了两个地方,后续说明)。
所以当时得出的总结是 1, this总是指向当前调用者,2,使用this.field可以创建全局变量。
在上面的代码再添加行代码
第二次代码
function Person(str){
this.name=str;
this.age=25;
}
var p1=new Person('z3');
console.log(p1.name); //结果 z3
console.log(name); //结果 z3
console.log(p1.age); //结果25
console.log(age); // age is not defined
对这个结果一开始很不可思议,怎么name没问题,age 就变成了没有定义。
想了一会想不通之后, 打开firebug, 运行之后查看window这个对象有没有age这个变量(如果有就是全局变量)。一看果然没有
只有一个Person对象及这个对象的实例 p1。 那这个name是怎么回事? 继续看了下window相关的属性,居然看到了这么个东东
居然还有window.name这个属性,而且值默认是空字符""; 也就是说下面这样的代码完全可以执行,没有undefined, 也没有 xx is not defined
<script type=text/javascript>
alert(name);
</script>
把上面代码再做一个修改
第三次代码
function Person(str){
this.name=str;
age=25;
}
var p1=new Person('z3');
console.log(p1.name); //结果 z3
console.log(name); //结果 z3
console.log(p1.age); //结果 undefined
console.log(age); // 25
这一下就了然了,首先this只是代表指向当前调用者,this.field 不会创建全局变量。
第二个打印结果是正确的 是因为 name这个全局变量不是通过this.name创建的 而是window自带了一个name这个属性,并且默认值为""。通过this.name赋值,只是把window.name的默认值覆盖了。
第三个打印结果为undefined 原因很简单,age=25 是全局变量要调用只能是window.age或age。通过p1.age,只能是声明了一个变量但是未赋值,所以打印出来就是undefined
目前只是知道window对象中有name这个属性,而且它的作用很广,其中有个重要的作用是可以解决js中同源策略的问题。