JavaScript 标准库

参考基础教程的整理,方便记忆

一、Object对象 (O大写)

  • 所有其他对象都继承自这个对象。Object本身也是一个构造函数,可以直接通过它来生成新对象。
    • 作为构造函数使用时,可以接受一个参数。参数若为对象,则直接返回原对象;若是一个原始类型的值,则返回该值对应的包装对象。
  • Object.keys(只返回可枚举的属性)和Object.getOwnPropertyNames(返回不可枚举的属性名。),一般用来遍历对象的属性。
    • 参数都是一个对象,都返回一个数组,该数组的成员都是对象自身的(而不是继承的)所有属性名。
    • 一般都使用Object.keys方法,遍历数组的属性。
var a = ["Hello", "World"];

Object.keys(a)
// ["0", "1"]

Object.getOwnPropertyNames(a)
// ["0", "1", "length"]
  • 对象属性模型的相关方法

    • Object.getOwnPropertyDescriptor():获取某个属性的attributes对象。
    • Object.defineProperty():通过attributes对象,定义某个属性。
    • Object.defineProperties():多个属性。
    • Object.getOwnPropertyNames():返回直接定义在某个对象上面的全部属性的名称。
  • 控制对象状态的方法

    • Object.preventExtensions():防止对象扩展。
    • Object.isExtensible():判断对象是否可扩展。
    • Object.seal():禁止对象配置。
    • Object.isSealed():判断一个对象是否可配置。
    • Object.freeze():冻结一个对象。
    • Object.isFrozen():判断一个对象是否被冻结。
  • 原型链相关方法

    • Object.create():指定原型对象和属性,返回一个新的对象。
    • Object.getPrototypeOf():获取对象的Prototype对象。
  • Object实例对象的方法,主要有以下六个。

    • valueOf():返回当前对象对应的值。
    • toString():返回当前对象对应的字符串形式。
    • toLocaleString():本地字符串形式。
      hasOwnProperty():判断某个属性是否为当前对象自身的属性,还是继承自原型对象的属性。
    • isPrototypeOf():判断当前对象是否为另一个对象的原型。
    • propertyIsEnumerable():判断某个属性是否可枚举。
  • Object.prototype.valueOf()作用是返回一个对象的“值”,默认情况下返回对象本身。

var o = new Object();
o.valueOf() === o // true
  • Object.prototype.toString()作用是返回一个对象的字符串形式,默认情况下返回类型字符串。也可判断数据类型。

二、Array 对象

  • Array是JavaScript的内置对象,同时也是一个构造函数,可以用它生成新的数组。(不同的参数,会导致它的行为不一致。)
  • Array.isArray()用来判断一个值是否为数组。
var a = [1, 2, 3];

typeof a // "object"
Array.isArray(a) // true
//typeof运算符只能显示数组-的类型是Object,而Array.isArray方法可以对数组返回true。
  • valueOf返回数组本身。toString返回数组的字符串形式。
  • push方法用于在数组的末端添加一个或多个元素,并返回添加新元素后的数组长度。会改变原数组。
var a = [];
a.push(1) 
//合并两个数组
var a = [1, 2, 3];
var b = [4, 5, 6];

Array.prototype.push.apply(a, b)
// 或者
a.push.apply(a, b)

// 等同于
a.push(4, 5, 6)

a // [1, 2, 3, 4, 5, 6]
  • 可向对象添加元素,添加后的对象变成类似数组的对象,即新加入元素的键对应数组的索引,并且对象有一个length属性。
var a = {a: 1};

[].push.call(a, 2);
a // {a:1, 0:2, length: 1}

[].push.call(a, [3]);
a // {a:1, 0:2, 1:[3], length: 2}
  • pop方法用于删除数组的最后一个元素,并返回该元素。注意,该方法会改变原数组。
    • 对空数组使用pop方法,不会报错,而是返回undefined。
    • push和pop结合使用,就构成了“后进先出”的栈结构(stack)。
  • join方法以参数作为分隔符,将所有数组成员组成一个字符串返回。如果不提供参数,默认用逗号分隔
var a = [1, 2, 3, 4];

a.join(' ') // '1 2 3 4'
a.join(' | ') // "1 | 2 | 3 | 4"
a.join() // "1,2,3,4"
  • concat方法用于多个数组的合并。它将新数组的成员,添加到原数组的尾部,然后返回一个新数组,原数组不变。

  • shift用于删除数组的第一个元素,并返回该元素。注意,该方法会改变原数组。

    • shift可以遍历并清空一个数组。
    • push和shift结合使用,就构成了“先进先出”的队列结构(queue)。
  • unshift方法用于在数组的第一个位置添加元素(可多个),并返回添加新元素后的数组长度。会改变原数组。

  • reverse用于颠倒数组中元素的顺序,返回改变后的数组。改变原数组。

  • slice(起始,终止(不包含在内))用于提取原数组的一部分,返回一个新数组,原数组不变。

    • 若参数是负数,则表示倒数计算的位置。
    • 如果参数值大于数组成员的个数,或者第二个参数小于第一个参数,则返回空数组。
  • splice(起始,个数,被插入数组的新元素(可有可无))删除原数组的一部分成员,并可以在被删除的位置添加入新的数组成员,返回值是被删除的元素。会改变原数组。

  • sort方法对数组成员进行排序,默认是按照字典顺序排序。排序后,原数组将被改变。数值会被先转成字符串。

  • map方法对数组的所有成员依次调用一个函数,根据函数结果返回一个新数组。原数组没有变化。

    • 遍历字符串的每个字符要通过函数的call方法间接使用,或者先将字符串转为数组。
    • 接受一个函数作为参数。该函数调用时,map方法会将其传入三个参数,分别是当前成员、当前位置和数组本身。
    • map方法不会跳过undefined和null,但是会跳过空位.
  • forEach与map很相似,但无返回值。(可接受第二个参数,用来绑定回调函数的this关键字。)

    • forEach无法中断执行,会将所有成员遍历完。若需符合某种条件时,中断遍历,用for循环。
  • filter的参数是一个函数,所有数组成员依次执行该函数,返回结果为true的成员组成一个新数组返回。该方法不会改变原数组。

  • some(),every()用来判断数组成员是否符合某种条件

    • every则是所有数组成员的返回值都是true,才返回true。
    • some是只要有一个数组成员的返回值是true则为ture。
  • reduce方法和reduceRight方法依次处理数组的每个成员,最终累计为一个值。它们的差别是,reduce是从左到右处理,reduceRight相反
    第一个参数都是一个函数。该函数接受以下四个参数。

    • 累积变量,默认为数组的第一个成员(必须)
    • 当前变量,默认为数组的第二个成员(必须)
    • 当前位置(从0开始)(可选)
    • 原数组(可选)
  • indexOf方法返回给定元素在数组中第一次出现的位置,如果没有出现则返回-1。indexOf方法还可以接受第二个参数,表示搜索的开始位置。

  • lastIndexOf方法返回给定元素在数组中最后一次出现的位置,如果没有出现则返回-1。如果数组中包含NaN,这两个方法不适用,即无法确定数组成员是否包含NaN。

三、包装对象

var v1 = new Number(123);
var v2 = new String('abc');
var v3 = new Boolean(true);
//生成了三个对象,与原始值的类型不同。

typeof v1 // "object"
typeof v2 // "object"
typeof v3 // "object"

v1 === 123 // false
v2 === 'abc' // false
v3 === true // false
  • valueOf方法返回包装对象实例对应的原始类型的值。
new Number(123).valueOf()  // 123
new String("abc").valueOf() // "abc"
new Boolean("true").valueOf() // tru
  • toString方法返回实例对应的字符串形式
  • 原始类型的自动转换
'abc'.length // 3
//abc是一个字符串,本身不是对象,不能调用length属性。
//自动将其转为包装对象,调用length属性。
//调用结束后,这个临时对象就会被销毁。
//只读的,无法修改。字符串无法添加新属性。
'abc'.charAt === String.prototype.charAt
// true
  • 如果包装对象与原始类型值进行混合运算,包装对象会转化为原始类型(实际是调用自身的valueOf方法)。
new Number(123) + 123 // 246
new String('abc') + 'abc' // "abcabc"
  • Boolean 对象
if (new Boolean(false)) {
  console.log('true');
} // true
// false对应的包装对象实例是一个对象,进行逻辑运算时,
//被自动转化成布尔值true(所有对象对应的布尔值都是true)
if (new Boolean(false).valueOf()) {
  console.log('true');
} // 无输出
//实例的valueOf方法,则返回实例对应的原始值,本例为false。
if (Boolean(null)) {
  console.log('true');
} // 无输出

if (new Boolean(null)) {
  console.log('true');
} // true
//对于一些特殊值,Boolean对象前面加不加new
//会得到完全相反的结果

四、 Number对象

  • 数值对应的包装对象,可以作为构造函数使用(用于生成值为数值的对象。),也可以作为工具函数使用。
var n = new Number(1);
typeof n // "object"
  • 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。
  • Number.prototype.toString()
    接受一个参数,表示输出的进制。如果省略这个参数,默认将数值先转为十进制,再输出字符串
(10).toString(2) // "1010"
(10).toString(8) // "12"
//前面的数值要加括号或加两个点(即理解为10.0.)
10..toString(2)
10 .toString(2) // "1010"
10.0.toString(2) // "1010"
  • Number.prototype.toFixed()
    • 转为指定位数的小数,返回这个小数对应的字符串。
      参数为指定的小数位数,有效范围为0到20,超出这个范围将抛出RangeError错误。
  • Number.prototype.toExponential()
    • 将一个数转为科学计数法形式。
    • 参数表示小数点后有效数字的位数,范围为0到20,超出这个范围,会抛出一个RangeError。
  • Number.prototype.toPrecision()
    • 将一个数转为指定位数的有效数字参数为有效数字的位数,范围是1到21,超出这个范围会抛出RangeError错误(不太可靠,跟浮点数不是精确储存有关。)
  • 自定义方法

五、String对象

  • 生成字符串的包装对象。
  • 实际上,字符串的包装对象是一个类似数组的对象(即很像数组,实质上不是数组)。
new String("abc")
// String {0: "a", 1: "b", 2: "c", length: 3}
  • String对象还可将任意类型的值转为字符串。
  • String.fromCharCode()
    • String对象提供的静态方法(即定义在对象本身,而非对象实例),主要是fromCharCode()。参数是一系列Unicode码点(传入的参数不能大于0xFFFF),返回对应的字符串。
  • charAt()返回指定位置的字符,参数是从0开始编号的位置。
  • charCodeAt方法返回给定位置字符的Unicode码点(十进制表示),相当于String.fromCharCode()的逆操作。
    • charCodeAt方法返回的Unicode码点不大于65536(0xFFFF)(两个字节的字符的码点)。否则必需连续使用两次charCodeAt,读入charCodeAt(i),和charCodeAt(i+1),将两个16字节放在一起,才能得到准确的字符。
    • 如果参数为负数,或大于等于字符串的长度,charCodeAt返回NaN。
  • concat方法用于连接两个字符串,返回一个新字符串,不改变原字符串。
'a'.concat('b', 'c') // "abc"
//可以接受多个参数

六、Math对象

  • 该对象不是构造函数,不能生成实例,所有的属性和方法都必须在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的平方根。
  • 方法

    • Math.abs():绝对值
    • Math.ceil():向上取整
    • Math.floor():向下取整
    • Math.max():最大值
    • Math.min():最小值
    • Math.pow():指数运算
    • Math.sqrt():平方根
    • Math.log():自然对数
    • Math.exp():e的指数
    • Math.round():四舍五入
    • Math.random():随机数
  • 三角函数方法

    • Math.sin():返回参数的正弦
    • Math.cos():返回参数的余弦
    • Math.tan():返回参数的正切
    • Math.asin():返回参数的反正弦(弧度值)
    • Math.acos():返回参数的反余弦(弧度值)
    • Math.atan():返回参数的反正切(弧度值)

七、Date对象

  • 日期和时间的操作接口。可表示1970年1月1日00:00:00前后的各1亿天(单位为毫秒)。
Date()
// "Tue Dec 01 2015 09:34:43 GMT+0800 (CST)"
//可作为普通函数直接调用,返回一个代表当前时间的字符串。
Date(2000, 1, 1)
// "Tue Dec 01 2015 09:34:43 GMT+0800 (CST)"
//即使带有参数,Date作为普通函数使用时,返回的还是当前时间。
  • 可当构造函数使用。使用new命令,会返回一个Date对象的实例。不加参数,生成代表当前时间的对象。
var today = new Date();
var today = new Date();

today
// "Tue Dec 01 2015 09:34:43 GMT+0800 (CST)"

// 等同于
today.toString()
// "Tue Dec 01 2015 09:34:43 GMT+0800 (CST)"
//这个Date实例对应的字符串值,就是当前时间。
  • new Date(milliseconds)

    • Date对象接受从1970年1月1日00:00:00 UTC开始计算的毫秒数作为参数。Unix时间戳(单位为秒)作为参数,须将Unix时间戳乘以1000。
new Date(1378218728000)
// Tue Sep 03 2013 22:32:08 GMT+0800 (CST)

// 1970年1月2日的零时
var Jan02_1970 = new Date(3600 * 24 * 1000);
// Fri Jan 02 1970 08:00:00 GMT+0800 (CST)

// 1969年12月31日的零时
var Dec31_1969 = new Date(-3600 * 24 * 1000);
// Wed Dec 31 1969 08:00:00 GMT+0800 (CST)
//Date构造函数的参数可以是一个负数,表示1970年1月1日之前的时间。
  • new Date(datestring),(month day, year hours:minutes:seconds)接受一个日期字符串作为参数,返回所对应的时间。
new Date('January 6, 2013');
// Sun Jan 06 2013 00:00:00 GMT+0800 (CST)
//省略了小时、分钟或秒数会被设为0。
  • 月份从0开始计算,但是,天数从1开始计算。另外,除了日期默认为1,小时、分钟、秒钟和毫秒默认都是0。
  • 最少需要提供两个参数(年和月),其他参数都是可选的,默认等于0。
new Date(2013)
// Thu Jan 01 1970 08:00:02 GMT+0800 (CST)
//只有一个参数,2013被解释为毫秒数,而不是年份。
new Date(2013, 15)
// Tue Apr 01 2014 00:00:00 GMT+0800 (CST)
//这些参数如果超出了正常范围,会被自动折算。
new Date(2013, 0, -1)
// Sun Dec 30 2012 00:00:00 GMT+0800 (CST)
//参数还可以使用负数,表示扣去的时间。
new Date(1, 0)
// Tue Jan 01 1901 00:00:00 GMT+0800 (CST)

new Date(-1, 0)
// Fri Jan 01 -1 00:00:00 GMT+0800 (CST)
//年份如果是0到99,会自动加上1900。
//如果为负数,则表示公元前。
  • 类型转换时,Date对象的实例如果转为数值,则等于对应的毫秒数;如果转为字符串,则等于对应的日期字符串。
d1 = new Date(2000, 2, 1);
var d2 = new Date(2000, 3, 1);

d2 - d1
// 2678400000
//减法运算,返回的就是它们间隔的毫秒数
d2 + d1
// "Sat Apr 01 2000 00:00:00 GMT
//+0800 (CST)Wed Mar 01 2000 00:00:00 GMT+0800 (CST)"
//加法运算,返回的就是连接后的两个字符串
  • Date.now返回当前距离1970年1月1日 00:00:00 UTC的毫秒数(Unix时间戳乘以1000)。
Date.now() // 1364026285194
  • Date.parse方法用来解析日期字符串,返回距离1970年1月1日 00:00:00的毫秒数标准YYYY-MM-DDTHH:mm:ss.sssZ,其他格式也可以被解析。
  • Date对象返回当前时区的时间。Date.UTC可以返回UTC时间(世界标准时间)。
// 格式
Date.UTC(year, month[, date[, hrs[, min[, sec[, ms]]]]])

// 用法
Date.UTC(2011, 0, 1, 2, 3, 4, 567)
// 1293847384567
  • Date实例对象的方法
  • to类:从Date对象返回一个字符串,表示指定的时间。
    • Date.prototype.toString()返回一个完整的日期字符串
    • Date.prototype.toUTCString()返回对应的UTC时间,比北京时间晚8个小时。
    • Date.prototype.toISOString()返回对应时间的ISO8601写法。(UTC时区)
    • Date.prototype.toJSON()返回一个符合JSON格式的ISO格式的日期字符串,与toISOString相同。
    • Date.prototype.toDateString()返回日期字符串。
    • Date.prototype.toTimeString()返回时间字符串。
    • Date.prototype.toLocaleDateString()返回一个字符串,代表日期的当地写法。
    • Date.prototype.toLocaleTimeString()返回一个字符串,代表时间的当地写法。
  • get类:获取Date对象的日期和时间。
    • getTime():返回距离1970年1月1日00:00:00的毫秒数,等同于valueOf方法。
    • getDate():返回实例对象对应每个月的几号(从1开始)。
    • getDay():返回星期几,星期日为0,星期一为1,以此类推。
    • getYear():返回距离1900的年数。
    • getFullYear():返回四位的年份。
    • getMonth():返回月份(0表示1月,11表示12月)。
    • getHours():返回小时(0-23)。
    • getMilliseconds():返回毫秒(0-999)。
    • getMinutes():返回分钟(0-59)。
    • getSeconds():返回秒(0-59)。
    • getTimezoneOffset():返回当前时间与UTC的时区差异,以分钟表示,返回结果考虑到了夏令时因素。
      这些get*方法返回的都是当前时区的时间
  • Date对象还提供了这些方法对应的UTC版本,用来返回UTC时间。
    • getUTCDate()
    • getUTCFullYear()
    • getUTCMonth()
    • getUTCDay()
    • getUTCHours()
    • getUTCMinutes()
    • getUTCSeconds()
    • getUTCMilliseconds()
  • set类:设置Date对象的日期和时间。
    • setDate(date):设置实例对象对应的每个月的几号(1-31),返回改变后毫秒时间戳。
    • setYear(year): 设置距离1900年的年数。
    • setFullYear(year [, month, date]):设置四位年份。
    • setHours(hour [, min, sec, ms]):设置小时(0-23)。
    • setMilliseconds():设置毫秒(0-999)。
    • setMinutes(min [, sec, ms]):设置分钟(0-59)。
    • setMonth(month [, date]):设置月份(0-11)。
    • setSeconds(sec [, ms]):设置秒(0-59)。
    • setTime(milliseconds):设置毫秒时间戳。
      这些跟get*方法一一对应的,但是没有setDay方法,因为星期几是计算出来的,而不是设置的。
var d2 = new Date ('January 6, 2013');
d2.setDate(-1) // 1356796800000
d2 // Sun Dec 30 2012 00:00:00 GMT+0800 (CST)
//set*方法的参数都会自动折算
//参数超过当月的最大天数,向下一个月顺延
//参数是负数,从上个月的最后一天开始减去的天数。
  • set*系列方法除了setTime()和setYear(),都有对应的UTC版本,即设置UTC时区的时间。
    • setUTCDate()
    • setUTCFullYear()
    • setUTCHours()
    • setUTCMilliseconds()
    • setUTCMinutes()
    • setUTCMonth()
    • setUTCSeconds()
  • Date.prototype.valueOf()返回实例对象距离1970年1月1日00:00:00 UTC对应的毫秒数,该方法等同于getTime方法。可以用于计算精确时间。
var d = new Date();
d.valueOf() // 1362790014817
d.getTime() // 1362790014817

八、RegExp对象

  • 正则表达式(regular expression)是一种表达文本模式(即字符串结构)的方法。
var regex = /xyz/;
//使用字面量,以斜杠表示开始和结束。编译时新建正则表达式
var regex = new RegExp('xyz');
//使用 RegExp 构造函数。运行时新建正则表达式。
  • 可以接受第二个参数,表示修饰符
var regex = new RegExp('xyz', "i");
// 等价于
var regex = /xyz/i;
  • 1.属性
  • 修饰符相关,返回布尔值,表示是否设置。
    • ignoreCase:i
    • global:g
    • multiline:m
      返回布尔值,表示是否设置了i,g,m修饰符,该属性只读。
  • 与修饰符无关的属性。
    • lastIndex:返回下一次开始搜索的位置。可读写,只在设置了g修饰符时有意义。
    • source:返回正则表达式的字符串形式(不包括反斜杠),只读。
  • test()返回一个布尔值,表示当前模式是否能匹配参数字符串。
/cat/.test('cats and dogs') // true
  • exec()返回匹配结果。若匹配,返回一个数组(每一个匹配成功的子字符串),否则返回null。
    exec方法的返回数组包含属性:
    • input:整个原字符串。
    • index:整个模式匹配成功的开始位置(从0开始计数)。
  • 字符串对象的方法
    • match():返回一个数组(所有匹配的子字符串。)
    • search():搜索,返回一个整数,表示匹配开始的位置。
    • replace():替换,返回替换后的字符串。
    • split():分割,返回一个数组(分割后的各个成员。)
  • 如果正则表达式带有g修饰符,则该方法与正则对象的exec方法行为不同,会一次性返回所有匹配成功的结果。
  • String.prototype.search(搜索模式,替换的内容),返回第一个满足条件的匹配结果在整个字符串中的位置,可替换。如果没有任何匹配返回-1。
'aaa'.replace('a', 'b') // "baa"
'aaa'.replace(/a/, 'b') // "baa"
//不加g修饰符,就替换第一个匹配成功的值
'aaa'.replace(/a/g, 'b') // "bbb"
//否则替换所有匹配成功的值。
  • replace方法的第二个参数可以使用美元符号$,用来指代所替换的内容。
    • $& 指代匹配的子字符串。
    • $` 指代匹配结果前面的文本。
    • $' 指代匹配结果后面的文本。
    • $n 指代匹配成功的第n(从1开始)组内容。
    • $$ 指代美元符号$。
  • String.prototype.split()按照正则规则分割字符串,返回一个由分割后的各个部分组成的数组。
    • str.split(separator, [limit])(分隔规则,返回数组的最大成员数)
// 非正则分隔
'a,  b,c, d'.split(',')
// [ 'a', '  b', 'c', ' d' ]

// 正则分隔,去除多余的空格
'a,  b,c, d'.split(/, */)
// [ 'a', 'b', 'c', 'd' ]

// 指定返回数组的最大成员
'a,  b,c, d'.split(/, */, 2)
[ 'a', 'b' ]

匹配规则

  • 1.字面量字符(只表示它字面的含义)和元字符(有特殊含义,不代表字面的意思)
  • 元字符
    • 点字符(.)匹配除回车(\r)、换行(\n) 、行分隔符(\u2028)和段分隔符(\u2029)以外的所有字符。
/c.t/
//c.t匹配c和t之间包含任意一个字符的情况
//只要这三个字符在同一行,比如cat、c2t、c-t等等,但是不匹配coot
  • 位置字符用来提示字符所处的位置,主要有两个字符。
    • ^ 表示字符串的开始位置
    • $ 表示字符串的结束位置
  • 选择符(|)
    竖线符号(|)在正则表达式中表示“或关系”(OR),即cat|dog表示匹配cat或dog。
    1. 转义符
      正则表达式中那些有特殊含义的字符,如果要匹配它们本身,就需要在它们前面要加上反斜杠。比如要匹配加号, \ +。
/1+1/.test('1+1')
// false

/1\+1/.test('1+1')
// true
  • 正则模式中,需要用斜杠转义的,一共有12个字符:^、.、[、$、(、)、|、*、+、?、{ 和 \ \,需要特别注意的是,如果使用RegExp方法生成正则对象,转义需要使用两个斜杠,因为字符串内部会先转义一次。
(new RegExp('1\+1')).test('1+1')
// false

(new RegExp('1\\+1')).test('1+1')
// true
    1. 特殊字符
      \cX 表示Ctrl-[X],其中的X是A-Z之中任一个英文字母,用来匹配控制字符。
      [\b] 退格键(U+0008),不要与\b混淆。
      \n 换行键。
      \r 回车键。
      \t 制表符tab(U+0009)。
      \v 垂直制表符(U+000B)。
      \f 换页符(U+000C)。
      \0 null字符(U+0000)。
      \xhh 匹配一个以两位十六进制数(\x00-\xFF)表示的字符。
      \uhhhh 匹配一个以四位十六进制数(\u0000-\uFFFF)表示的unicode字符。
  • 4.字符类(class)
    • 表示有一系列字符可供选择,只要匹配其中一个就可以了。所有可供选择的字符都放在方括号内,如[xyz] 表示x、y、z之中任选一个匹配。
  • 脱字符(^)
    如果方括号内的第一个字符是[ ^ ],则表示除了字符类之中的字符,其他字符都可以匹配。比如,[^xyz]表示除了x、y、z之外都可以匹配。
    • 脱字符只有在字符类的第一个位置才有特殊含义,否则就是字面含义
  • 连字符(-)
    表示字符的连续范围。[abc]可以写成[a-c]
    1. 预定义模式
    • \d [0-9]。
    • \D 0-9以外,[^0-9]。
    • \w 任意的字母、数字和下划线,[A-Za-z0-9_]。
    • \W [^A-Za-z0-9_]。
    • \s 匹配空格(包括制表符、空格符、断行符等),相等于[\t\r\n\v\f]。
    • \S [^\t\r\n\v\f]。
    • \b 匹配词的边界。
    • \B 匹配非词边界,即在词的内部。
      正则表达式遇到换行符(\n)就会停止匹配。
  • 6.重复类
    模式的精确匹配次数,使用大括号({ })表示。{n}恰好重复n次,{n,}至少重复n次,{n,m}不少于n次,不多于m次。
    1. 量词符用来设定某个模式出现的次数。
    • ? 问号表示某个模式出现0次或1次,等同于{0, 1}。
    • *星号表示某个模式出现0次或多次,等同于{0,}。
    • +加号表示某个模式出现1次或多次,等同于{1,}。
  • 8 .贪婪模式
    ? * + 默认情况下都是最大可能匹配,即匹配直到下一个字符不满足匹配规则为止。
var s = 'aaa';
s.match(/a+/) // ["aaa"]
//因为默认是贪婪模式,会一直匹配到字符a不出现为止,所以匹配结果是3个a
  • 9.修饰符(modifier)
    模式的附加规则,放在正则模式的最尾部。 可单个使用或多个一起使用。
    • g修饰符
      默认情况下,第一次匹配成功后,正则对象就停止向下匹配了。g修饰符表示全局匹配(global),加上它以后,正则对象将匹配全部符合条件的结果,主要用于搜索和替换。
    • i修饰符
      默认情况下,正则对象区分字母的大小写,加上i修饰符以后表示忽略大小写(ignorecase)。
    • m修饰符
      表示多行模式(multiline),会修改 ^ 和$的行为。默认情况下(即不加m修饰符时),^ 和$匹配字符串的开始处和结尾处,加上m修饰符以后,^ 和$还会匹配行首和行尾,即识别换行符(\n)。
    1. 组匹配
  • 正则表达式的括号表示分组匹配,括号中的模式可以用来匹配分组的内容。
/fred+/.test('fredd') // true
//没有括号,结果+只表示重复字母d
/(fred)+/.test('fredfred') // true
//有括号,结果+就表示匹配“fred”这个词。
  • 使用组匹配时,不宜同时使用g修饰符,否则match方法不会捕获分组的内容。
  • 非捕获组
    (?:x)称为非捕获组(Non-capturing group),表示不返回该组匹配的内容,即匹配的结果中不计入这个括号。
var m = 'abc'.match(/(?:.)b(.)/);
m // ["abc", "c"]
//第一个括号是非捕获组,所以最后返回的结果中没有第一个括号,只有第二个括号匹配的内容。
  • 先行断言
    x(?=y)称为先行断言(Positive look-ahead),x只有在y前面才匹配,y不会被计入返回结果。
var m = 'abc'.match(/b(?=c)/);
m // ["b"]
//括号里的部分是不会返回的。
  • 先行否定断言
    x(?!y)称为先行否定断言(Negative look-ahead),x只有不在y前面才匹配,y不会被计入返回结果。

九、 JSON 格式

  • 一种用于数据交换的文本格式目的是取代繁琐笨重的 XML 格式。
  • 每个 JSON 对象是简单类型的值或复合类型的值,只能是一个值,每个 JSON 文档只能包含一个值。
  • JSON 对值的类型和格式的严格规定。
    • 复合类型的值只能是数组或对象,不能是函数、正则表达式对象、日期对象。
    • 简单类型的值只有四种:字符串、数值(十进制)、布尔值和null(不能用NaN, Infinity, -Infinity和undefined)。
    • 字符串必须使用双引号表示,不能使用单引号。
    • 对象的键名必须放在双引号里面。
    • 数组或对象最后一个成员的后面,不能加逗号。
  • JSON.stringify()用于将一个值转为字符串。该字符串符合 JSON 格式,并且可以被JSON.parse方法还原。
    • 如果原始对象中,有一个成员的值是undefined、函数或 XML 对象,这个成员会被过滤。
    • 正则对象会被转成空对象。
JSON.stringify(/foo/) // "{}"
  • JSON.stringify会忽略对象的不可遍历属性。
    • JSON.stringify可接受一个数组作为第二个参数,指定需要转成字符串的属性。第二个参数还可以是一个函数,用来更改JSON.stringify的默认行为。
    • 递归处理中,每一次处理的对象都是前一次返回的值。
    • JSON.stringify还可接受第三个参数,用于增加返回的JSON字符串的可读性。如果是数字,表示每个属性前面添加的空格(最多不超过10个);如果是字符串(不超过10个字符),则该字符串会添加在每行前面。
    • 如果对象有自定义的toJSON方法,那么JSON.stringify会使用这个方法的返回值作为参数,而忽略原对象的其他属性。
  • toJSON将正则对象自动转为字符串。JSON.stringify默认不能转换正则对象,设置了toJSON方法以后,就可以转换正则对象了。
  • JSON.parse()方法用于将JSON字符串转化成对象。
    • 要求有效格式
    • 为了处理解析错误,可以放在try...catch代码块中。
    • JSON.parse方法可以接受一个处理函数,与JSON.stringify方法类似。

十、console

Console面板(又称为控制台)

  • 用途:
    • 调试程序,显示网页代码运行时的错误信息。
    • 提供了一个命令行接口,用来与网页代码互动
  • 浏览器实现
    • Elements:查看网页的HTML源码和CSS代码。
    • Resources:查看网页加载的各种资源文件(比如代码文件、字体文件、css文件等),以及在硬盘上创建的各种内容(比如本地缓存、Cookie、Local Storage等)。
    • Network:查看网页的 HTTP 通信情况。
    • Sources:查看网页加载的所有源码。
    • Timeline:查看各种网页行为随时间变化的情况。
    • Performance:查看网页的性能情况,比如 CPU 和内存消耗。
    • Console:用来运行 JavaScript 命令。
  • console 对象的方法
  • 1.console.log()
    • 在控制台输出信息。可接受多个参数,将结果连接起来输出。
    • 自动在每次输出的结尾,添加换行符。
    • 如果第一个参数是格式字符串(使用了格式占位符),将依次用后面的参数替换占位符再输出。
  • console.log方法支持以下占位符,不同格式的数据必须使用对应格式的占位符。
    • %s 字符串
    • %d 整数
    • %i 整数
    • %f 浮点数
    • %o 对象的链接
    • %c CSS格式字符串
  • console.info()
  • console.debug()
    • 都是console.log方法的别名,用法完全一样。console.info方法会在输出信息的前面有蓝色图标。
  • console.warn()黄色三角,console.error()红色的叉
    • 在控制台输出信息,表示出错,会显示错误发生的堆栈。其他与log都一样。
    • log方法是写入标准输出(stdout),warn方法和error方法是写入标准错误(stderr)。
  • console.table方法可以将某些复合类型的数据,转为表格显示。
    • 复合型数据转为表格显示的条件是,必须拥有主键。数组->数字键、对象->最外层键。
  • console.count()用于计数,输出它被调用了多少次。
  • console.dir()用来对一个对象进行检查(inspect),并以易于阅读和打印的格式显示。
 console.log({f1: 'foo', f2: 'bar'})
// Object {f1: "foo", f2: "bar"}

console.dir({f1: 'foo', f2: 'bar'})
// Object
//   f1: "foo"
//   f2: "bar"
//   __proto__: Object
//显示dir方法的输出结果,比log方法更易读,信息也更丰富。
//该方法对于输出 DOM 对象非常有用,因为会显示 DOM 对象的所有属性。
  • console.dirxml()主要用于以目录树的形式,显示 DOM 节点。
console.dirxml([1, 2, 3])
// 等同于
console.dir([1, 2, 3])
//-如果参数不是 DOM 节点,而是普通的 JavaScript 对象,console.dirxml等同于console.dir。
  • console.assert(表达式,字符串)
    • 在程序运行过程中进行条件判断,若不满足条件,显示一个错误,但不会中断程序执行。相当于提示用户,内部状态不正确。
    • 只有当第一个参数为false,才会提示有错误,在控制台输出第二个参数,否则不会有任何结果。
console.assert(false, '判断条件不成立')
// Assertion failed: 判断条件不成立

// 相当于
try {
  if (false) {
    throw new Error('判断条件不成立');
  }
} catch(e) {
  console.error(e);
}
  • console.time(),console.timeEnd()
    这两个方法用于计时,可以算出一个操作所花费的准确时间。
    • time方法表示计时开始,timeEnd方法表示计时结束。它们的参数是计时器的名称。调用timeEnd方法之后,console窗口会显示“计时器名称: 所耗费的时间”。
  • console.profile(),console.profileEnd()
    • console.profile方法用来新建一个性能测试器(profile),它的参数是性能测试器的名字。
    • console.profileEnd方法用来结束正在运行的性能测试器。
  • console.group(),console.groupend(),console.groupCollapsed()
    • console.group和console.groupend这两个方法用于将显示的信息分组。它只在输出大量信息时有用,分在一组的信息,可以用鼠标折叠/展开。
    • console.groupCollapsed方法与console.group方法相似,区别是该组的内容在第一次显示时是收起的(collapsed)。
  • console.trace(),console.clear()
    • console.trace方法显示当前执行的代码在堆栈中的调用路径。
    • console.clear方法用于清除当前控制台的所有输出,将光标回置到第一行。如果用户选中了控制台的“Preserve log”选项,网页脚本调用console.log将不起作用,但手动在控制台执行该方法依然有效。
  • 命令行 API
    • $_属性返回上一个表达式的值。
    • $0 - $4,控制台保存了最近5个在Elements面板选中的DOM元素,$0代表倒数第一个,$1代表倒数第二个,直到$4。
    • $(selector)返回第一个匹配的元素,等同于document.querySelector()。如果页面脚本对$有定义,则会覆盖原始的定义。
    • $$(selector)返回一个选中的DOM对象,等同于document.querySelectorAll。
    • $x(path)返回一个数组,包含匹配特定XPath表达式的所有DOM元素。
    • inspect(object)打开相关面板,并选中相应的元素:DOM元素在Elements面板中显示,JavaScript对象在Profiles面板中显示。
    • getEventListeners(object)返回一个对象,该对象的成员为登记了回调函数的各种事件,每个事件对应一个数组,数组的成员为该事件的回调函数。
    • keys(object),values(object)
      keys(object)方法返回一个数组,包含特定对象的所有键名。
      values(object)方法返回一个数组,包含特定对象的所有键值。
    • monitorEvents(object[, events]) 监听特定对象上发生的特定事件。当这种情况发生时,会返回一个Event对象,包含该事件的相关信息。
    • unmonitorEvents(object[, events])用于停止监听。
      允许监听同一大类的事件。所有事件可以分成四个大类:
      • mouse:”mousedown”, “mouseup”, “click”, “dblclick”, “mousemove”, “mouseover”, “mouseout”, “mousewheel”
      • key:”keydown”, “keyup”, “keypress”, “textInput”
      • touch:”touchstart”, “touchmove”, “touchend”, “touchcancel”
      • control:”resize”, “scroll”, “zoom”, “focus”, “blur”, “select”, “change”, “submit”, “reset”
  • profile([name]),profileEnd()
    profile方法用于启动一个特定名称的CPU性能测试,profileEnd方法用于结束该性能测试。
  • clear():清除控制台的历史。
    copy(object):复制特定DOM元素到剪贴板。
    dir(object):显示特定对象的所有属性,是console.dir方法的别名。
    dirxml(object):显示特定对象的XML形式,是console.dirxml方法的别名。
  • debugger用于除错,设置断点。如果有正在运行的除错工具,程序运行到debugger语句时会自动停下。没有除错工具,debugger语句不会产生任何结果,自动跳过这一句。

十一、属性描述对象

  • 一个内部数据结构,用来描述一个对象的属性的行为,控制它的行为。每个属性都有自己对应的属性描述对象,保存该属性的一些元信息。
  • 6个元属性。
    • value该属性的属性值,默认为undefined。
    • writable存放一个布尔值,表示属性值(value)是否可改变,默认为true。
    • enumerable(可枚举性)存放一个布尔值,默认为true。如果设为false,会使得某些操作(比如for...in循环、Object.keys())跳过该属性。
    • configurable(可配置性)存放一个布尔值,默认为true。false时将阻止某些操作改写该属性。
    • get(getter),默认undefined。
    • set(setter),默认undefined。
  • Object.getOwnPropertyDescriptor方法可以读出对象自身属性的属性描述对象。
var o = { p: 'a' };

Object.getOwnPropertyDescriptor(o, 'p')
// Object { value: "a",
//   writable: true,
//   enumerable: true,
//   configurable: true
// }
  • Object.defineProperty(),Object.defineProperties()
    允许通过定义属性描述对象,来定义或修改一个属性,然后返回修改后的对象。格式:Object.defineProperty(object, propertyName, attributesObject),它的writable、configurable、enumerable这三个属性的默认值都为false。
  • 可枚举性(enumerable)
    用来控制所描述的属性,是否将被包括在for...in循环之中。如果为false
    • for..in(包括继承自原型对象的属性)
    • Object.keys(只返回对象本身的属性)
    • JSON.stringify方法不会取到该属性。
      只有可枚举的属性,才会被for...in循环遍历,同时还规定原生继承的属性都是不可枚举的。
    • 如果需要获取对象自身的所有属性,不管是否可枚举,可以使用Object.getOwnPropertyNames方法
  • 可配置性(configurable)
    决定了是否可以修改属性描述对象。也就是说,当configurable为false的时候,value、writable、enumerable和configurable都不能被修改了。
    • writable只有在从false改为true会报错,从true改为false则是允许的。
    • value,只要writable和configurable有一个为true,就允许改动。
    • configurable为false时,若直接对该属性赋值,不报错但不会成功。
    • 可配置性决定了一个变量是否可以被删除(delete)。
    • var声明变量时其configurable为false。否则(或者使用属性赋值的方式声明变量),变量的可配置性为true。
    • 如果一个变量是使用var命令生成的,就无法用delete命令删除。也就是说,delete只能删除对象的属性。
  • 可写性(writable)
    决定了属性的值(value)是否可以被改变
  • Object.getOwnPropertyNames
    返回直接定义在某个对象上面的全部属性的名称,而不管该属性是否可枚举。
    • 一般系统原生的属性(非用户自定义的属性)都是不可枚举的。
  • Object.prototype.propertyIsEnumerable()用来判断一个属性是否可枚举。
var o = {};
o.p = 123;

o.propertyIsEnumerable('p') // true
o.propertyIsEnumerable('toString') // false
//用户自定义的p属性是可枚举的,而继承自原型对象的toString属性是不可枚举的。
  • 存取器(accessor)
    • 除了直接定义,属性还可以用存取器定义。get 和set。
    • 存取器提供的是虚拟属性(实际不存在),是每次读取时计算生成的。可实现每个属性禁止赋值等。
    • 存取器也可通过Object.defineProperty、Object.create定义。
    • 可以实现数据对象与DOM对象的双向绑定。
  • 对象的拷贝,可以通过Object.defineProperty方法来拷贝属性。
  • 控制对象状态
    JavaScript提供了三种方法,精确控制一个对象的读写状态,防止对象被改变。最弱一层的保护是Object.preventExtensions,其次是Object.seal,最强的Object.freeze。
    • Object.preventExtensions方法可以使得一个对象无法再添加新的属性。(可以用delete命令删除它的现有属性。)
    • Object.isExtensible方法用于检查一个对象是否使用了Object.preventExtensions方法。也就是说,检查是否可以为一个对象添加属性。
    • Object.seal方法使得一个对象既无法添加新属性,也无法删除旧属性。
    • Object.isSealed方法用于检查一个对象是否使用了Object.seal方法。
    • Object.freeze()可以使得一个对象无法添加新属性、无法删除旧属性、也无法改变属性的值,使得这个对象实际上变成了常量。
    • Object.isFrozen方法用于检查一个对象是否使用了Object.freeze()方法。
    • 局限性
      上面的方法锁定对象的可写性有一个漏洞,依然可以通过改变原型对象,来为对象增加属性。可把原型也冻结住解决。
      另外一个局限是,如果属性值是对象,上面这些方法只能冻结属性指向的对象,而不能冻结对象本身的内容。

推荐阅读更多精彩内容