1.基本类型与引用类型(J:基本类型标识,Y:引用类型标识)
基本类型:Undefined,Null,Boolean,Number,String。
引用类型:Object
1.1复制变量值
J 基本类型之间复制变量值为创建新值:
var num1=5;
var num2=num1;
num2=3;
alert(num2); //3
alert(num1); //5
num1与num2相互独立,当num2被赋值其他值时,对num1无影响。
Y 引用类型之间复制变量值为指向同一对象:
var obj1=new Object();
var obj2=obj1;
obj1.name='First';
alert(obj2.name); //'First'
obj1与obj2会相互影响。
1.2 传递参数
由函数外将参数传递到函数内使用的方式是按值传递。
Y 在引用类型传递参数时,书中用以下代码来验证引用类型传递参数也是按值传递
function setName(obj){
obj.name='First';
obj=new Object();
obj.name='Second';
}
var person=new Object();
setName(person);
alert(person.name); //'First'
它想说明在函数内obj重新引用新对象时与之前的对象脱离,即没有对person对象进行重置。但是以下代码证明在全局中(非函数参数传递时),引用新对象依然会与之前的对象脱离。
var obj1=new Object();
obj1.name='First';
var obj2=obj1;
alert(obj1.name); //‘First'
alert(obj2.name); //'First'
obj2=new Object();
obj2.name='Second';
alert(obj1.name); //'First'
alert(obj2.name); //'Second'
所以无法说明引用类型在传递参数时是按值传递而不是按引用传递。(等有机会找证明到底是怎么传递)
1.3 检测类型
typeof:检测类型
instanceof:检测是什么类型的对象
alert(person instanceof Object); //变量person是Object吗?
alert(colors instanceof Array); //变量colors是Array吗?
alert(pattern instanceof RegExp); //变量pattern是RegExp吗?
2. 执行环境及作用域
a. 在进入一个执行环境时,会查询标识符(变量),js中会生成一个作用域链,从作用域链的开头一直寻找到结尾(结尾部分为全局变量),当寻找完作用域链而没有找到标识符时则会报错。
b. 每个变量都有自己的作用域,超出作用域时无法访问。
var Test_1=1;
function a(){
var Test_2=2;
function b(){
var Test_3=3;
Test_1=5;
}
}
alert(Test_1); //5
alert(Test_3); //会报错
a示例:在函数b()中,会根据作用域链先在函数b()中寻找Test_1;没有,然后在函数a()中寻找Test_1;没有,然后再全局中找到Test_1。
b示例:在全局中调用Test_3会报错,因为Test_3的作用域只是在函数b()中。
3. 垃圾收集
垃圾收集方式有两种:标记清除与引用计数(Netscape Navigatro3,IE9之前)
标记清除:垃圾收集器运行时先标记所有的变量,然后再去除环境中的变量以及被环境中的变量引用的变量标记。在此之后再被加上的标记将被视为准备删除的变量,环境中的变量已经无法访问到这些变量。最后完成内存清除工作。
管理内存:局部变量在退出执行环境时会被自动清除,但是全局变量却不会。所以最好的方法就是在使用完全局变量后手动解除引用。
function createPerson(name){
var localPerson=new Object();
localPerson.name=name;
return localPerson;
}
var globalPerson=createPerson('First');
alert(globalPerson.name);
//手动解除globalPerson的引用
globalPerson=null;
localPerson在运行完函数createPerson()后自动被消除,但是globalPerson并没有,所以需要我们将手动接触globalPerson的引用。这样垃圾收集器在下次运行时就会清除掉globalPerson之前的值。