JavaScript 标准参考教程(alpha)笔记——标准库
http://javascript.ruanyifeng.com/#introduction
3.1.1 Object
对象的原生方法分成两类:Object
本身的方法与Object
的实例方法。
(1)Object对象本身的方法就是直接定义在Object对象的方法。
Object.print = function (o) { console.log(o) }; 结果:ƒ (o) { console.log(o) }
(2)Object的实例方法就是定义在Object原型对象Object.prototype
上的方法。它可以被Object
实例直接使用。
Object.prototype.print = function () {//Object.prototype定义了一个print方法 console.log(this); }; var obj = new Object();//生成一个Object的实例obj obj.print() // Object /*obj直接继承了Object.prototype的属性和方法,可以直接使用obj.print调用print方法,即实质就是调用Object.prototype.print方法*/
prototype 属性使您有能力向对象添加属性和方法。
3.1.2 Object是一个函数但可以当工具使用,可以将任意值转变为对象。
Object
函数的参数是各种原始类型的值,转换成对象就是原始类型值对应的包装对象,若参数是对象则返回该对象。
A instanceof B ,返回值为boolean类型,用来判断A是否是B的实例对象或者B子类的实例对象。
3.1.3 Object还可以当构造函数使用即生成新的对象。
var obj = new Object();
Object(value)
:将value转为对象;new Object(value)
:生成一个新的对象。
3.1.4.1 Object.keys
方法和Object.getOwnPropertyNames
方法都用来遍历对象的属性。
这两个
方法的参数都是一个对象,返回一个数组。该数组的成员都是该对象自身的(而不是继承的)所有属性名。只是Object.getOwnPropertyNames
方法还返回不可枚举的属性名。
1、 var a = ['Hello', 'World']; Object.keys(a) // ["0", "1"] Object.getOwnPropertyNames(a) // ["0", "1", "length"] 2、 var obj = { p1: 123, p2: 456 }; Object.keys(obj) // ["p1", "p2"] Object.getOwnPropertyNames(obj) // ["p1", "p2"]
3.1.5.1 Object.prototype.valueOf()可自定义覆盖,JS自动类型转换时会默认调用这个方法。
3.1.5.2 Object.prototype.toString()可自定义覆盖,返回一个对象字符串形式,默认返回类型字符串。
3.1.5.3 toString() 可用于判断数据类型。
Object.prototype.toString.call(value) /*通过函数的call方法,可以在任意值上调用这个方法,帮助我们判断这个值的类型。*/
3.1.5.4 Object.prototype.toLocaleString()与toString
的返回结果相同,也是返回一个值的字符串形式。主要作用是留出一个接口,让不同的对象实现自己版本的toLocaleString。
3.1.5.5 Object.prototype.hasOwnProperty()接受一个字符串作为参数返回布尔值表示该实例对象自身具有该属性(非继承属性)。
3.2.1 不建议使用Array生成数组,且它生成的空数组读取的时候返回undefined,但该位置没有任何值,无键名。
3.2.2.1 Array.isArray()返回布尔值表示参数是否为数组。
3.2.3.1 所有对象都拥有valueOf
方法和toString
方法,valueOf
方法表示对该对象求值,数组则返回本身;数组的toString
方法返回数组的字符串形式。
var arr = [1, 2, 3, [4, 5, 6]]; arr.toString() // "1,2,3,4,5,6"
3.2.3.2 push
方法在数组的末端添加一或多个元素,并返回添加后的数组长度。pop
方法用于删除数组的最后一个元素,并返回该元素。注意,这两个方法都会改变原数组。对空数组使用pop,会返回undefined。push
和pop
结合使用,就构成了“后进先出”的栈结构(stack)。
var arr = []; arr.push(1, 2); arr.push(3); arr.pop(); arr // [1, 2]
3.2.3.3 shift/
方法用于 删除/添加 数组的第一个元素,并返回该元素。注意,这两个方法都会改变原数组。所以使用unshift
shift
方法可以遍历并清空一个数组。push
和shift
结合使用,就构成了“先进先出”的队列结构(queue)。unshift可以接受多个参数。
3.2.3.4 join方法可以指定参数作为分隔符使所有数组成员连接为一个字符串返回,默认逗号。若数组成员是undefined
或null
或空位,则被转成空字符串。通过call方法,它可用于字符串或类似数组的对象。不改变原数组。
var obj = { 0: 'a', 1: '',2: 'b', length: 3 }; Array.prototype.join.call(obj, '*') // 'a**b'
3.2.3.5 concat
方法用于多个数组的合并。它将新数组的成员,添加到原数组成员的后部,然后返回一个新数组,不改变原数组。concat
也接受其他类型的值作为参数。
3.2.3.6 reverse方法用于颠倒排列数组元素,改变并返回原数组。
3.2.3.7 slice方法提取目标数组的一部分并返回新数组,不改变原数组。
arr.slice(start, end);
/*若 start >= 数组.length || end<start 则返回空数组*/
若slice没有参数,相当返回原数组的拷贝。若slice方法的参数为负数,则表示倒数计算的位置。例:-2表示倒数第二个位置。
slice可以将类似数组的对象转为真正的数组,通过call方法。
Array.prototype.slice.call({ 0: 'a', 1: 'b', length: 2 }) // ['a', 'b'] Array.prototype.slice.call(document.querySelectorAll("div")); Array.prototype.slice.call(arguments);
3.2.3.8 splice
方法用于删除原数组的部分成员,并可在删除的位置添加新的数组成员,返回值是被删除的元素。注意,该方法会改变原数组。
arr.splice(start, count, addElement1, addElement2, ...);
/*start:起始位;count:被删除元素个数*/
若为负数即从倒数第几位开始。若想要是单纯插入元素,则第二个参数可以设为0。若只提供一个参数等同将原数组在指定位置拆为两个数组。
var a = [1, 2, 3, 4]; a.splice(-3, 2)//[2,3]
a//[1,4]
a.splice(2, 0, 1) //[]
a//[1,2,1,3,4] 在索引为1的位置插入2,没有删除元素,所以是[1,2,2,3,4]
a.splice(2) // [3, 4] a // [1, 2]
3.2.3.9 sort方法对数组成员排序,默认按字典顺序,改变原数组。
[10111, 1101, 111].sort() // [10111, 1101, 111] /*自定义sort方法*/ [10111, 1101, 111].sort(function (a, b) { return a - b; }) // [111, 1101, 10111]
3.2.3.10 map方法将数组所有成员依次传入参数函数,返回新数组,不改变原数组。map方法接受第二个参数,用来绑定回调函数内部的this变量。
var arr = ['a', 'b', 'c']; [1, 2].map(function (e) { return this[e]; }, arr) // ['b', 'c']
/*通过第二个参数回调函数内部的this对象,指向arr数组*
若数组有空位,map方法的回调函数不会在此位置执行,会跳过,但不会跳过undefined和null。
3.2.3.11 forEach
方法与map
方法很相似,但forEach
方法不返回值,所以如果数组遍历要返回值则用map,否则用forEach
。forEach
的用法与map
方法一致,参数是一个函数,该函数同样接受三个参数:当前值、当前位置、整个数组。
function log(element, index, array) { console.log('[' + index + '] = ' + element); } [2, 5, 9].forEach(log); // [0] = 2 // [1] = 5 // [2] = 9
/*上面代码forEach
遍历数组不是为了得到返回值,而是为了在屏幕输出内容,所以不必使用map
方法。*
forEach
方法也可以接受第二个参数,绑定参数函数的this
变量。
var out = []; [1, 2, 3].forEach(function(elem) { this.push(elem * elem); }, out); out // [1, 4, 9]
空数组out
是forEach
方法的第二个参数,结果,回调函数内部的this
关键字就指向out
。forEach
方法也会跳过数组的空位,但不会跳过undefined
和null
。
注意,forEach
方法无法中断执行,总是会将所有成员遍历完。如果希望符合某种条件时,就中断遍历,要使用for
循环。
3.2.3.12 filter
方法的参数是一个函数,用于过滤数组成员,返回结果为true的成员组成新数组返回,不改变原数组。
var arr = [0, 1, 'a', false]; arr.filter(Boolean) // [1, "a"] /*filter方法返回数组arr里面所有布尔值为true的成员。*/
filter
方法的参数函数也可以接受三个参数,也还可以接受第二个参数,绑定参数函数内部的this变量。
3.2.3.13 some(),every()两个方法返回布尔值判断数组成员是否符合某种条件,接受一个函数作为参数,该函数接受三个参数。some只要有一个成员返回值为true则整个some方法返回true;而every需要所有成员返回值为true才返回true。
注意,对于空数组,some
方法返回false
,every
方法返回true
,回调函数都不会执行。这两个方法都接受第二参数用来绑定参数函数内部的this
变量。
3.2.3.14 reduce
方法和reduceRight
方法依次处理数组的每个成员,最终累计为一个值。差别:reduce
从左到右处理,reduceRight
则是从右到左,其他完全一样。且第一个参数都是函数,该函数接受以下四个参数:
- 累积变量,默认为数组的第一个成员
- 当前变量,默认为数组的第二个成员
- 当前位置(从0开始)
- 原数组
前两个必须,后两个可选。
reduce
方法和reduceRight
方法的第二个参数可以对累积变量指定初值,数组从初值开始累加。(对空数组尤其 有用,加为空数组取不到初始值,而给它一个默认的初始值则不会报错。)
这两个方法会遍历数组,因而可以做一些有关遍历的操作比如找出字符长度最长的数组成员。
3.2.3.15 indexOf/
方法返回给定元素在数组中 第一次/最后一次 出现的位置,若无该元素则返回lastIndexOf
-1
,且indexOf
接受第二个参数,表示搜索的开始位置。
注意,这两个方法不能用来搜索NaN
的位置,因为它们内部使用===运算符进行比较,而NaN是唯一一个不等于本身的值。
3.2.3.16 上面这些数组方法返回的还是数组的可以链式使用。
var users = [ {name: 'tom', email: 'tom@example.com'}, {name: 'peter', email: 'peter@example.com'} ]; users .map(function (user) { return user.email; }) .filter(function (email) { return /^t/.test(email); }) .forEach(console.log); // "tom@example.com" /*先产生一个所有 Email 地址组成的数组,然后再过滤出以t开头的 Email 地址。*/
3.3.1 三种原始类型的值——数值、字符串、布尔值——在一定条件下,也会自动转为对象即原始类型的“包装对象”。而“包装对象”就是它们所对应的原生对象——Number
、String
、Boolean,这三个值可以把它们包装成对象。总结:这三个原生对象带有new时,将原始类型的值转为对象,不带new作为普通函数使用时将任意类型的值转为原始类型的值。
3.3.2.1 valueOf
方法返回包装对象实例对应的原始类型的值。
3.3.2.2 toString
方法返回对应的字符串形式。
3.3.3 原始类型的值,可以自动当作对象调用,即调用各种对象的方法和参数。且自动转换生成的包装对象是只读的,无法修改,调用后马上自动销毁,再次调用则为一个新的对象而非原来的。
如果要为字符串添加属性,只有在它的原型对象String.prototype
上定义。
3.3.4 在包装对象的原型上添加自定义方法和属性,供原始类型的值直接调用。
String.prototype.double = function () { return this.valueOf() + this.valueOf(); }; 'abc'.double() // abcabc Number.prototype.double = function () { return this.valueOf() + this.valueOf(); }; (123).double() // 246 /*123外面必须要加上圆括号,否则后面的点运算符(.)会被解释成小数点。*/
3.3.5.1 注意,false
对应的包装对象实例,布尔运算结果也是true
。
if (new Boolean(false)) { console.log('true'); } // true if (new Boolean(false).valueOf()) { console.log('true'); } // 无输出 /*因为false对应的包装对象实例是一个对象,而所有对象对应的布尔值都是true。但实例的valueOf方法,则返回实例对应的原始值,结果为false。*/
3.3.5.2 使用双重的否运算符(!
)也可以将任意值转为对应的布尔值。
/*记住这几种为true的情况*/ Boolean(1) // true Boolean('false') // true Boolean([]) // true Boolean({}) // true Boolean(function () {}) // true Boolean(/foo/) // true
对于一些特殊值,Boolean
对象前面加不加new
,会得到完全相反的结果,必须小心。
if (Boolean(false)) { console.log('true'); } // 无输出 if (new Boolean(false)) { console.log('true'); } // true if (Boolean(null)) { console.log('true'); } // 无输出 if (new Boolean(null)) { console.log('true'); } // true
3.4 1 加new构造函数,生成数值对象;不加new为工具函数将任何类型的值转为数值。
3.4.2 Number对象拥有以下属性。
Number.POSITIVE_INFINITY
:正的无限,指向Infinity
。Number.NEGATIVE_INFINITY
:负的无限,指向-Infinity
。Number.NaN
: 表示非数值,指向NaN
。Number.MAX_VALUE
: 表示最大的正数,相应的,最小的负数为-Number.MAX_VALUE
。Number.MIN_VALUE
: 表示最小的正数(即最接近0的正数,在64位浮点数体系中为5e-324
),相应的,最接近0的负数为-Number.MIN_VALUE
。Number.MAX_SAFE_INTEGER
: 表示能够精确表示的最大整数,即9007199254740991
。Number.MIN_SAFE_INTEGER
: 表示能够精确表示的最小整数,即-9007199254740991
。
3.4.3.1 Number.prototype.toString()将数值转为字符串,可以接受一个参数代表输出的进制,默认十进制,数值加上括号再引用,例(10).toString()或者
10..toString()或者
10 .toString()或者
10.0.toString(2),这意味着可以对一个小数使用toString方法,通过方括号运算符也可以调用,注意它只能将十进制的数转为其他进制的字符串,如果要将其他进制转为十进制,需要用到parseInt方法。
3.4.3.2 Number.prototype.toFixed()将一个数转为指定位数的小数,返回对应的字符串。参数为小数位数,范围0到20,例(10).toFixed(2) // "10.00"
。
3.4.3.3 Number.prototype.toExponential()将一个数转为科学计数法形式,参数是小数点后的有效数字的位数,范围0到20,例(10).toExponential(2) // "1.00e+1"
。
3.4.3.4 Number.prototype.toPrecision()将一个数转为指定位数的有效数字,参数为有效数字的位数,范围是1到21,例(12.34).toPrecision(5) // "12.340"
。
3.4.4 Number.prototype
对象上面可以自定义方法,被Number
的实例继承,可以根据实际情况进行链式运算。
注意,数值的自定义方法,只能定义在它的原型对象Number.prototype
上面,数值本身是无法自定义属性的。
var n = 1; n.x = 1; n.x // undefined
上面代码中,n
是一个原始类型的数值。直接在它上面新增一个属性x
,不会报错,但毫无作用,总是返回undefined
。这是因为一旦被调用属性,n
就自动转为Number
的实例对象,调用结束后,该对象自动销毁。所以,下一次调用n
的属性时,实际取到的是另一个对象,属性x
当然就读不出来。
3.5.1 字符串对象是一个类似数组的对象(很像数组,但不是数组)。构造函数。
new String('abc') // String {0: "a", 1: "b", 2: "c", length: 3} (new String('abc'))[1] // "b" /*字符串abc对应的字符串对象,有数值键(0、1、2)和length属性,所以可以像数组那样取值。*/
3.5.2.1 String.fromCharCode()是定义在对象本身的静态方法,参数是一个或多个数值,代表 Unicode 码点,返回值是这些码点组成的字符串。范围小于0xFFFF
,而码点大于0xFFFF
的字符的四字节表示法,由 UTF-16 编码方法决定。
3.5.3.1 String.prototype.length返回字符串的长度。
3.5.4.1 String.prototype.charAt()返回指定位置的字符,参数从0开始,若小于0或大于字符长度返回空字符串( "" ),数组下标可以替代这个方法。
3.5.4.2 String.prototype.charCodeAt()返回字符串指定位置的 Unicode 码点(十进制表示),相当于String.fromCharCode()
的逆操作。参数为负数,或大于等于字符串的长度,返回NaN
。且返回的 Unicode 码点不会大于65536(0xFFFF),也就是说,只返回两个字节的字符的码点。若遇到码点大于 65536 的字符(四个字节的字符),必需连续使用两次charCodeAt
,不仅读入charCodeAt(i)
,还要读入charCodeAt(i+1)
,将两个值放在一起,才能得到准确的字符。
3.5.4.3 String.prototype.concat()连接两个字符串,返回一个新字符串,不改变原字符串。接受多个参数且会先将不是字符串的参数转化为字符串进行连接。
3.5.4.4 String.prototype.slice()从原字符串取出子字符串并返回,不改变原字符串。第一个参数开始,第二个参数结束(不含该位置),若省略第二个参数,默认从开始到结束,若为负值,表示从结尾开始倒数计算的位置,即该负值加上字符串长度。若第一个参数大于第二个参数则返回空字符串。
'JavaScript'.slice(-6) // "Script" 'JavaScript'.slice(0, -6) // "Java" 'JavaScript'.slice(-2, -1) // "p"
3.5.4.5 String.prototype.substring()从原字符串取出子字符串并返回,不改变原字符串,跟slice
方法很相像。但当第二个参数大于第一个参数,substring
方法会自动更换两个参数的位置。若参数是负数,substring
方法会自动将负数转为0。优先使用slice。
'Javascript'.substring(-3) // "JavaScript" 'JavaScript'.substring(4, -3) // "Java"
3.5.4.6 String.prototype.substr()从原字符串取出子字符串并返回,不改变原字符串,跟slice
和substring
方法的作用相同。如果第二个参数是负数,将被自动转为0,因此会返回空字符串。
3.5.4.7 String.prototype.indexOf(),String.prototype.lastIndexOf()确定一个字符串在另一个字符串中第一次出现的位置,返回结果是匹配开始的位置。如果返回-1
,就表示不匹配。indexOf
接受第二个参数,表示从该位置开始向后匹配。lastIndexOf
的第二个参数表示从该位置起向前匹配。
3.5.4.8 String.prototype.trim()去除字符串两端的空格(不仅是空格,还包括制表符(
、v
)、换行符(
)和回车符(
)。),返回一个新字符串,不改变原字符串。
3.5.4.9 String.prototype.toLowerCase()/String.prototype.toUpperCase() 将一个字符串全部转为 小写/大写 。它们都返回一个新字符串,不改变原字符串。
3.5.4.10 String.prototype.match()
3.5.4.11 String.prototype.search(),String.prototype.replace()。search
方法的用法基本等同于match
,但是返回值为匹配的第一个位置。如果没有找到匹配,则返回-1
。replace
方法用于替换匹配的子字符串,一般情况下只替换第一个匹配(除非使用带有g
修饰符的正则表达式)。search
方法和replace
方法都可以使用正则表达式作为参数。
3.5.4.12 String.prototype.split()按照给定规则分割字符串,返回一个由分割出来的子字符串组成的数组。split
方法的第二个参数,决定了返回数组的成员数。 split
方法还可以使用正则表达式作为参数
'a|b|c'.split('|') // ["a", "b", "c"] 'a|b|c'.split('') // ["a", "|", "b", "|", "c"] /*分割规则为空字符串,则返回数组的成员是原字符串的每一个字符。*/ 'a|b|c'.split() // ["a|b|c"] /*省略参数,则返回数组的唯一成员就是原字符串。*/ /*若分割规则的部分处于字符串的开头或结尾或紧紧相邻,则返回数组的第一个或最后一个成员是一个空字符串。*/ 'a||c'.split('|') // ['a', '', 'c']
3.5.4.13 String.prototype.localeCompare()比较两个字符串。它返回一个整数 小于0/等于0/大于0,表示 第一个字符串 小于/等于/大于 第二个字符串。最大特点:考虑自然语言的顺序。举例来说,正常情况下Unicode 码点比较大写的英文字母小于小写字母,但是它大写的大于小写的。可以有第二个参数,指定所使用的语言(默认是英语),然后根据该语言的规则进行比较。
3.6 Math不是构造函数不生成实例,所有的属性和方法都必须在Math
对象上调用。
3.6.1 Math
对象的静态属性,提供以下一些数学常数。
Math.E
:常数e
。Math.LN2
:2 的自然对数。Math.LN10
:10 的自然对数。Math.LOG2E
:以 2 为底的e
的对数。Math.LOG10E
:以 10 为底的e
的对数。Math.PI
:常数 Pi。Math.SQRT1_2
:0.5 的平方根。Math.SQRT2
:2 的平方根。
3.6.2 Math
对象提供以下一些静态方法。
Math.abs()
:绝对值Math.ceil()
:向上取整Math.floor()
:向下取整Math.max()
:最大值Math.min()
:最小值Math.pow()
:指数运算Math.sqrt()
:平方根Math.log()
:自然对数Math.exp()
:e的指数Math.round()
:四舍五入Math.random()
:随机数
3.6.2.2 Math.max()/Math.min() 如果参数为空, 返回 -Infinity
/Infinity
。
3.6.2.3 Math.floor(),Math.ceil()可以结合起来,实现一个总是返回数值的整数部分的函数。
3.6.2.4 Math.round(),注意,它对负数的处理(主要是对0.5
的处理)。
Math.round(0.5) // 1
Math.round(-1.1) // -1 Math.round(-1.5) // -1 Math.round(-1.6) // -2
3.6.2.7 Math.log()返回以e
为底的自然对数值。如果要计算以10为底的对数,可以先用Math.log
求出自然对数,然后除以Math.LN10
;求以2为底的对数,可以除以Math.LN2
。
Math.log(100)/Math.LN10 // 2
Math.log(8)/Math.LN2 // 3
3.6.2.10 三角函数方法
Math.sin()
:返回参数的正弦(参数为弧度值)Math.cos()
:返回参数的余弦(参数为弧度值)Math.tan()
:返回参数的正切(参数为弧度值)Math.asin()
:返回参数的反正弦(返回值为弧度值)Math.acos()
:返回参数的反余弦(返回值为弧度值)Math.atan()
:返回参数的反正切(返回值为弧度值)
3.7 Date()对象 http://javascript.ruanyifeng.com/stdlib/date.html
3.8 RegExp对象 http://javascript.ruanyifeng.com/stdlib/regexp.html
元字符,不代表自身,使用时前需加上 "" 。正则表达式中,需要反斜杠转义的,一共有12个字符:^
、.
、[
、$
、(
、)
、|
、*
、+
、?
、{
和\
。需要特别注意的是,如果使用RegExp
方法生成正则对象,转义需要使用两个斜杠,因为字符串内部会先转义一次。因为RegExp
作为构造函数,参数是一个字符串。但是,在字符串内部,反斜杠也是转义字符,所以它会先被反斜杠转义一次,然后再被正则表达式转义一次,因此需要两个反斜杠转义。
量词符从0开始计数、?