《JavaScript高级程序设计》第4-5章
第四章 变量、作用域和内存问题
1、基本类型和引用类型的值
1)动态的属性
2)复制变量值:当从一个变量向另一个变量复制引用类型的值时,同样也会将存储在变量对象中的值复制一份放到为新变量分配的空间中。
3)传递参数:参数只能按值传递;在向参数传递基本类型的值时,被传递的值会被复制给一个局部变量(命名参数);在向参数传递引用类型的值时,会把这个值在内存中的地址复制给一个局部变量。
4)检测类型:instanceof
2、执行环境及作用域
1)全局执行环境:在Web浏览器中,全局执行环境是window对象,因此所有全局变量和函数都是作为window对象的属性和方法创建的
2)作用域链:内部环境可以通过作用域链访问所有的外部环境,但外部环境不能访问内部环境中的任何变量和函数。局部环境开始时会先在自己的变量对象中搜索变量和函数名,如果搜索不到则再搜索上一级作用域链。
3)延长作用域链:try-catch语句的catch块、witch语句
4)没有块级作用域
3、垃圾收集
1)标记清除:垃圾收集器在运行的时候会给存储在内存中的所有变量都加上标记,然后它会去掉环境中的变量以及被环境中的变量引用的变量的标记,而在此之后再被加上标记的变量将被视为准备删除的变量原因是环境中的变量已经无法访问到这些变量了。
2)引用计数:当声明了一个变量并将一个引用类型值赋给该变量时,则这个值的引用次数加1;如果同一个值又被赋给另一个变量,则该值的引用次数减1。
3)性能问题:如果垃圾收集例程回收的内存分配量低于15%,则变量、字面量和(或)数组元素的临界值加倍;如果例程回收了85%的内存分配量,则将各种临界值重置为默认值。
4)管理内存:解除引用
第五章 引用类型
1、Object类型
1)创建Object:使用new操作符后跟Object构造函数;使用对象字面量表示法
2)访问对象属性:点表示法;使用方括号表示法,将要访问的属性以字符串的形式放在方括号中
2、Array类型
1)创建Array:使用new操作符后跟Array构造函数;使用数组字面量表示法,数组字面量由一对包含数组项的方括号表示,多个数组项之间以逗号分隔
2)检测数组:Array.isArray()方法,IE9+、Firefox4+、Safari5+、Opera10.5+、Chrome有效
3)转换方法:toLocaleString()、toString()返回由数组中每个值的字符串形式拼接而成的一个以逗号分隔的字符串;valueOf()返回数组;join()则可以使用不同的分隔符来创建这个字符串
4)栈方法:LIFO后进先出;push()推入,可以接收任意数量的参数,把它们逐个添加到数组末尾,并返回修改后数组的长度;pop()移除,从数组末尾移除最后一项,减少数组的length值,然后返回移除的项
5)队列方法:FIFO先进先出;push()向数组的末尾添加项,shift()移除数组中的第一个项并返回该项,同时该数组长度减1;unshift()在数组前端添加任意个项并返回新数组的长度,pop()从数组的末尾移除项
6)重排序方法:reverse()反转数组项的顺序;sort()按升序排列数组项,调用每个数组项的toString(),然后比较得到的字符串;sort()可以接收一个比较函数作为参数
升序比较函数:
Function compare(value1,value2){
If(value1<value2){
return -1;
}else If(value1>value2){
return 1;
}else{
return 0;
}
}
降序比较函数:
Function compare(value1,value2){
If(value1<value2){
return 1;
}else If(value1>value2){
return -1;
}else{
return 0;
}
}
7)操作方法:concat()基于当前数组中的所有项创建一个新数组;slice()基于当前数组中的一个或多个项创建一个新数组,可以接收一个或两个参数;splice()可以用于删除任意数量的项,需要指定2个参数——起始位置、要删除的项数,可以用于向任意位置插入任意数量的项,需要指定至少3个参数——起始位置、要删除的项数(0)、要插入的项,可以用于向指定位置插入任意数量的项,且同时删除任意数量的项,需要指定至少3个参数——起始位置、要删除的项数、要插入的项,始终返回一个数组,该数组中包含从原始数组中删除的项(如果没有删除任何项,则返回一个)
8)位置方法:indexOf()和lastIndexOf(),接收两个参数——要查找的项和表示起点位置的索引(可选),其中indexOf()从数组的开头开始向后查找,lastIndexOf()则从数组的末尾开始向前查找,IE9+、Firefox2+、Safari3+、Opera9.5+、Chrome有效
9)迭代方法:every()对数组中的每一项运行给定函数,如果该函数对每一项都返回true,则返回true;filter()对数组中的每一项运行给定函数,返回该函数会返回true的项组成的数组;forEach()对数组中的每一项运行给定函数,这个方法没有返回值;map()对数组中的每一项运行给定函数,返回每次函数调用的结果组成的数组;some()对数组中的每一项运行给定函数,如果该函数对任一项返回true,则返回true;IE9+、Firefox2+、Safari3+、Opera9.5+、Chrome有效
10)归并方法:reduce()和reduceRight()这两个方法都会迭代数组的所有项,然后构建一个最终返回的值,接收两个参数——在每个项上调用的函数、作为归并基础的初始值(可选),而在每个项上调用的函数接收四个参数——前一个值、当前值、项的索引和数组对象。其中reduce()方法从数组的第一项开始,逐个遍历到最后,而reduceRight()则从数组的最后一项开始,向前遍历到第一项
3、Date类型
使用new操作符后跟Date构造函数,参数可以使用Date.parse()接收一个表示日期的字符串参数,然后尝试根据这个字符串返回相应日期的毫秒数,也可以使用Date.UTC()接收的参数分别为年份(必需)、基于0的月份(0到11)(必需)、月中的哪一天(1到31)、小时数(0到23)、分钟、秒以及毫秒数;Date.now()返回表示调用这个方法时的日期和时间的毫秒数,使用+操作符获取Date对象的时间戳可以达到同样的效果,IE9+、Firefox3+、Safari3+、Opera10.5+、Chrome有效
4、RegExp类型
1)使用字面量来定义var expression = /pattern/flags,其中的模式(pattern)部分可以是任何简单或复杂的正则表达式,可以包含字符类、限定符、分组、向前查找以及反向引用;每个正则表达式都可带有一或多个标志(flags),用以标明正则表达式的行为,包括g(全局模式)、i(不区分大小写模式)、m(多行模式);模式中使用的所有元字符都必须转义,包括( { \ ^ $ | ) ? * + . ] };使用new操作符后跟RegExp构造函数,接收参数——pattern、flags都是字符串,模式中使用的所有元字符都必须双重转义\\
2)RegExp实例属性global(布尔值,是否设置了g标志)、ignoreCase(布尔值,是否设置了i标志)、lastIndex(整数,表示开始搜索下一个匹配项的字符位置,从0算起)、multiline(布尔值,是否设置了m标志)、source(正则表达式的字符串表示,按照字面量形式而非传入构造函数中的字符串模式返回)
3)RegExp实例方法exec(),接收一个字符串参数,然后返回包含第一个匹配项信息的数组,或者在没有匹配项的情况下返回null,返回的数组包含两个属性index(匹配项在字符串中的位置)和input(应用正则表达式的字符串);RegExp实例方法test(),接收一个字符串参数,在该模式与该参数匹配的情况下返回true,否则返回false
4)RegExp构造函数属性input(最近一次要匹配的字符串)、lastMatch(最近一次的匹配项)、lastParen(最近一次匹配的捕获组)、leftContext(input字符串中lastMatch之前的文本)、multiline(布尔值,表示是否所有表达式都使用多行模式)、rightContext(input字符串中lastMatch之后的文本)
5)模式的局限性:匹配字符串开始和结尾的\A和\Z锚、向后查找、并集和交集类、原子组、Unicode支持(单个字符除外)、命名的捕获组、s(single、单行)和x(free-spacing、无间隔)匹配模式、条件匹配、正则表达式注释
5、Function类型:
1)函数声明语法定义:
function sum(num1,num2){
return num1+num2;
}
函数表达式定义:
var sum=function(num1,num2){
return num1+num2;
}
2)使用不带圆括号的函数名是访问函数指针,而非调用函数
3)没有重载:声明了两个同名函数,而结果则是后面的函数覆盖了前面的函数
4)函数声明和函数表达式:解析器会率先读取函数声明,并使其在执行任何代码之前可用;至于函数表达式,则必须等到解析器执行到它所在的代码行,才会真正被解释执行
5)作为值的函数:
function callSomeFunction(someFunction,someArgument){
return someFunction(someArgument);
}
function creatComparisonFunction(propertyName){
return function(object1,object2){
var value1=object1[propertyName];
var value2=object2[propertyName];
if(value1<value2){
return -1;
}else if(value1>value2){
return 1;
}else{
return 0;
}
}
}
6)函数内部属性:callee属性:argument对象拥有callee属性,指向拥有这个arguments对象的函数;this属性:this引用的是函数据以执行的环境变量,当在网页的全局作用域中调用函数时,this对象引用的就是window
7)函数的属性和方法:每个函数都包含两个属性length(表示函数希望接收的命名参数的个数)和prototype(保存实例方法);每个函数都包含两个非继承而来的方法apply()(接收两个参数:一个是在其中运行函数的作用域,另一个是参数数组。其中第二个参数可以是Array实例,也可以是arguments对象)和call()(接收至少两个参数:第一个是在其中运行函数的作用域,其余参数都直接传递给函数),用于在特定的作用域中调用函数;bind()会创建一个函数的实例,其this值会被绑定到传给bind()函数的值
6、基本包装类型:Boolean、Number和String,使用new操作符创建的引用类型的实例,在执行流离开当前作用域之前都一直保存在内存中;而自动创建的基本包装类型的对象,则只存在于一行代码的执行瞬间,然后立即被销毁。
1)Number类型:toString()方法传递一个表示基数的参数,返回几进制数值的字符串形式;toFixed()方法传递一个表示小数位的参数,返回以指定的小数位表示的数值的字符串形式;toaExponential()方法传递一个表示指数的参数,返回以指数表示法表示的数值的字符串形式;toPrecision()方法可能会返回固定大小(fixed)格式,也可能返回指数(exponential)格式
2)String类型:
字符方法:charAt()返回以单字符形式的字符串,charCodeAt()返回字符编码,以方括号加数字索引来访问字符串中的特定字符;
字符串操作方法:concat()和加号操作符(“+”)拼接一或多个字符串,返回拼接后的字符串;slice()、substr()和substring()基于子字符串创建新字符串,接收一到两个参数,第一个参数指定子字符串的开始位置,slice()和substring()的第二个参数是子字符串最后一个字符的位置,substr()的第二个参数是返回的字符个数;slice()会将传入的负值与字符串的长度想加,substr()将负的第一个参数加上字符串的长度,而将负的第二个参数转换为0,substring()会把所有复制参数都转换为0
字符串位置方法:从一个字符串中搜索给定的子字符串,然后返回子字符串中的位置(如果没有找到该子字符串,则返回-1);indexOf()从字符串的开头向后搜索子字符串,第二个参数指定从该位置向后搜索,忽略该位置之前的所有字符;lastIndexOf()从字符串的末尾向前搜索子字符串,第二个参数指定从该位置向前搜索,忽略该位置之后的所有字符
trim()方法会创建一个字符串的副本,删除前置及后缀的所有空格,然后返回结果,IE9+、Firefox3.5+、Safari5+、Opera10.5+、Chrome有效;trimLeft()和trimRight()分别用于删除字符串开头和末尾的空格,Firefox3.5+、Safari5+、Chrome8+有效
字符串大小写转换方法:toLowerCase()、toLocal
字符串的模式匹配方法:match()只接收一个参数——正则表达式或RegExp对象,返回第一个匹配数组;search()只接收一个参数——正则表达式或RegExp对象,返回第一个匹配项的索引;replace()可以接收两个参数,第一个参数可以使一个RegExp对象或者一个字符串,第二个参数可以是一个字符串或者一个函数;split()基于指定的分隔符将一个字符串分割成多个子字符串,并将结果放在一个数组中,可以接收两个参数,第一个参数可以是一个字符串或一个RegExp对象,第二个参数可选用于指定数组的大小
localeCompare()方法:如果字符串在字母表中应该排在字符串参数之前则返回一个负数,之后则返回一个正数,相等则返回0;实现所支持的地区(国家和语言)决定了这个方法的行为
fromCharCode()方法:接收一或多个字符编码,然后将它们转换成一个字符串
7、单体内置对象
1)Global对象:
所有在全局作用域中定义的属性和函数,都是Global对象的属性;
URI编码方法:encodeURI()主要用于对整个URI进行编码,不会对本身属于URI的特殊字符进行编码;encodeURIComponent()主要用于对URI中的某一段进行编码,会对它发现的任何非标准字符进行编码;decodeURI()只能对使用encodeURI()替换的字符进行解码;decodeURIComponent()只能对使用deodeURIComponent()替换的字符进行解码
eval()方法:只接收一个参数——要执行的ECMAScript字符串;当解析器发现代码中调用eval()方法时,它会将传入的参数当作实际的ECMAScript语句来解析,然后把执行结果插入到原位置。通过eval()执行的代码被认为是包含该次调用的执行环境的一部分,因此被执行的代码具有与该执行环境相同的作用域链
Global对象的属性:特殊的值underfined、NaN、Infinity,以及所有原生引用类型的构造函数如Objec、Array、Function、Boolean、String、Number、Date、RegExp、Error
Window对象
2)Math对象
Math对象的属性:Math.E、Math.LN10、Math.LN2、Math.LOG2E、Math.LOG10E、Math.PI、Math.SQRT1_2、Math.SQRT2
Math.min()和Math.max()方法
舍入方法:Math.ceil()向上舍入,Math.floor()向下舍入,Math.round()标准舍入
Math.random()方法返回大于等于0小于1的一个随机数,值 = Math. floor(Math.random()*可能值的总数+第一个可能的值)