JS-标准对象

本文深入探讨了JavaScript中的标准对象,包括日期、正则表达式及JSON的使用技巧。详细讲解了Date对象的创建与操作,正则表达式的匹配与分组,以及JSON的序列化与反序列化过程。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

JS-标准对象

在JS世界里,一切都是对象。
可以用typeof操作符获取对象的类型,它总是返回一个字符串:

typeof 123; // 'number'
typeof NaN; // 'number'
typeof 'str'; // 'string'
typeof true; // 'boolean'
typeof undefined; // 'undefined'
typeof Math.abs; // 'function'
typeof null; // 'object'
typeof []; // 'object'
typeof {}; // 'object'

可见,numberstringbooleanundefinedobject有别于其他类型。值得注意的是:null、Array、{}都属于object

包装对象

JS还提供了包装对象,numberbooleanstring都有包装对象,包装对象用new创建,但是类型已经变为object了:

var n = new Number(123); // 123,生成了新的包装类型
var b = new Boolean(true); // true,生成了新的包装类型
var s = new String('str'); // 'str',生成了新的包装类型
n === 123; // false
b === true; // false
s === 'str' // false

此外,Number()Boolean()String()会被当成普通函数,把任何类型转换为numberbooleanstring类型。
总结有几条规则需要遵守:

  • 不要使用new Number()new Boolean()、**new String()**创建包装对象;
  • parseInt()parseFloat()来转换任意类型到number
  • 通常不必把任意类型转换为boolean再判断,因为可以直接写if (myVar) {…};
  • typeof操作符可以判断出numberbooleanstringfunctionundefined
  • 判断Array要使用Array.isArray(arr)
  • 判断null要使用myVar === null
  • 判断某个全局变量是否存在使用typeod window.myVar === 'undefined'
  • 判断函数内部某个变量是否存在使用typeof myVar === 'undefined'

Date


获取当前时间:

var now = new Date();
now; // Wed Feb 06 2019 21:34:28 GMT+0800 (中国标准时间)
now.getFullYear(); // 2019,  年份
now.getMonth(); // 1,   月份。注意范围是0~11,1表示二月
now.getDay(); // 3, 表示星期三
now.getHours(); // 21, 二十四小时制
now.getMinutes(); // 34,分钟
now.getSeconds(); // 28, 秒
now.getMilliseconds(); // 682,毫秒数
now.getTime(); // 1549460068682, 以number形式表示的时间戳

注意:当前获取时间是浏览器从本机操作系统获取的时间,所以不一定准确。

  • 创建Date
    创建时间的两种方法:
  1. 以年、月、日、时、分、秒、毫秒为参数创建:
var d = new Date(2015, 5, 19, 20, 15, 30, 123);
d; // Fri Jun 19 2015 20:15:30 GMT+0800 (CST)
  1. 解析一个符合ISO 8601格式的字符串:
var d = Date.parse('2015-06-24T19:49:22.875+08:00');
d; // 1435146562875

但它返回的不是Date对象,而是一个时间戳,不过很容易转换成一个Date

var d = new Date(1435146562875);
d; // Wed Jun 24 2015 19:49:22 GMT+0800 (CST)
d.getMonth(); // 5
  • 时区
    Date对象表示的时间总是按浏览器所在的时区显示的,不过我们既可以显示本地时间,也可以显示调整后的UTC时间:
var d = new Date(1435146562875);
d.toLocaleString(); // '2015/6/24 下午7:49:22',本地时间(北京时区+8:00),显示的字符串与操作系统设定的格式有关
d.toUTCString(); // 'Wed, 24 Jun 2015 11:49:22 GMT',UTC时间,与本地时间相差8小时

RegExp


正则表达式是一种匹配字符串的强有力的武器。

- 基础

  • \d可以匹配一个数字。
  • \w可以匹配一个数字或字母。
  • .可以匹配任意字符。
  • 特殊字符需要用\转义。
  • 要匹配变长的字符,在正则表达式中,用*表示任意个字符(包括0个),用+表示至少一个字符,用?表示0或1个字符,用{n}表示n个字符,用{n,m}表示n-m个字符。

- 进阶

要更精确地匹配,可以用[]表示范围,比如:
- [0-9a-zA-Z_]可以匹配一个数字、字母或者下划线;
- [0-9a-zA-Z_]+可以匹配至少由一个数字、字母或者下划线组成的字符串,比如’a100’,‘0_Z’,'js2015’等等;
- [a-zA-Z_$][0-9a-zA-Z_$]*可以匹配由字母或下划线、开头,后接任意个由一个数字、字母或者下划线、开头,后接任意个由一个数字、字母或者下划线、线组成的字符串,也就是JavaScript允许的变量名;
- [a-zA-Z_$][0-9a-zA-Z_$]{0, 19}更精确地限制了变量的长度是1-20个字符(前面1个字符+后面最多19个字符)。
- A|B可以匹配A或B。
- ^表示行的开头,$表示行的结束。比如:js也可以匹配'jsp',但加上^js$就只能匹配'js'了。

- RegExp

在JS中创建正则表达式有两种方式:
第一种是通过/正则表达式/写出来,第二种是通过new RegExp('正则表达式')创建一个RegExp对象。

var re1 = /ABC\-001/;
var re2 = new RegExp('ABC\\-001');

re1; // /ABC\-001/
re2; // /ABC\-001/

注意:第二种创建方式因为字符串转义的问题,字符串的两个\\实际上是一个\
RegExp对象的test()方法用于测试给定的字符串是否符合条件:

var re1 = /ABC\-001/;
var re2 = new RegExp('ABC\\-001');

re1; // /ABC\-001/
re2; // /ABC\-001/

- 切分字符串

用正则表达式切分字符串比用固定字符更灵活,正常的切分代码:

'a b   c'.split(' '); // ['a', 'b', '', '', 'c']

无法识别连续的空格,用正则表达式:

'a b   c'.split(/\s+/); // ['a', 'b', 'c']

加入,试试:

'a,b, c  d'.split(/[\s\,]+/); // ['a', 'b', 'c', 'd']

- 分组

正则表达式还是提取子串的功能。用()表示的是要提取的分组。

var re = /^(\d{3})-(\d{3,8})$/;
re.exec('010-12345'); // ['010-12345', '010', '12345']
re.exec('010 12345'); // null

定义了组,就可以在RegExp对象上用**exec()**方法提取出子串来。
exec()匹配成功后会返回一个字符串组,第一个元素是正则表达式匹配到的整个字符串,后面的子串表示匹配成功的子串。exec()匹配失败时会返回null
提取子串很有用,比如:

var re = /^(0[0-9]|1[0-9]|2[0-3]|[0-9])\:(0[0-9]|1[0-9]|2[0-9]|3[0-9]|4[0-9]|5[0-9]|[0-9])\:(0[0-9]|1[0-9]|2[0-9]|3[0-9]|4[0-9]|5[0-9]|[0-9])$/;
re.exec('19:05:30'); // ['19:05:30', '19', '05', '30']

- 贪婪匹配

正则匹配默认是贪婪匹配,也就是匹配尽可能多的字符,比如:

var re = /^(\d+)(0*)$/;
re.exec('102300'); // ['102300', '102300', '']

由于\d+采用贪婪匹配,直接把后面的0全部匹配了,结果0*只能匹配空字符串了。
加个?就可以让\d+采用非贪婪匹配(也就是尽可能少匹配)

var re = /^(\d+?)(0*)$/;
re.exec('102300'); // ['102300', '1023', '00']

- 全局搜索

JS正则表达式还有几个特殊的标志,最常用的是g,表示全局匹配:

var r1 = /test/g;
// 等价于:
var r2 = new RegExp('test', 'g');

全局匹配可以多次执行exec()方法来搜索一个匹配的字符串。当我们指定g标志后,每次运行exec(),正则表达式本身会更新lastIndex属性,表示上次匹配到的最后索引:

var s = 'JavaScript, VBScript, JScript and ECMAScript';
var re=/[a-zA-Z]+Script/g;

// 使用全局匹配:
re.exec(s); // ['JavaScript']
re.lastIndex; // 10

re.exec(s); // ['VBScript']
re.lastIndex; // 20

re.exec(s); // ['JScript']
re.lastIndex; // 29

re.exec(s); // ['ECMAScript']
re.lastIndex; // 44

re.exec(s); // null,直到结束仍没有匹配到

全局匹配类似搜索,因此不能使用/^…$/,那样只会最多匹配一次。
正则表达式还可以指定i标志,表示忽略大小写,m标志,表示执行多行匹配。

JSON


JSON是JavaScript Object Notation的缩写,它是一种数据交换格式。
JSON实际上是JavaScript的一个子集。在JSON中,一共这么几个数据类型:

  • number:和JavaScript的number完全一致;

  • boolean:就是JavaScript的true或false;

  • string:就是JavaScript的string;

  • null:就是JavaScript的null;

  • array:就是JavaScript的Array表示方式——[];

  • object:就是JavaScript的{ … }表示方式。
    以及上面的任意组合。
    并且,JSON还定死了字符集必须是UTF-8,表示多语言就没有问题了。为了统一解析,JSON的字符串规定必须用双引号"",Object的键也必须用双引号""。
    由于JSON非常简单,很快就风靡Web世界,并且成为ECMA标准。几乎所有编程语言都有解析JSON的库,而在JavaScript中,我们可以直接使用JSON,因为JavaScript内置了JSON的解析。

  • 序列化
    使用**JSON.string()**把任何JS对象序列化成一个JSON格式的字符串:

var xiaoming = {
    name: '小明',
    age: 14,
    gender: true,
    height: 1.65,
    grade: null,
    'middle-school': '\"W3C\" Middle School',
    skills: ['JavaScript', 'Java', 'Python', 'Lisp']
};
s; // {"name":"小明","age":14,"gender":true,"height":1.65,"grade":null,"middle-school":"\"W3C\" Middle School","skills":["JavaScript","Java","Python","Lisp"]}

输出的好看一点,加上参数,按缩进输出:

JSON.stringify(xiaoming, null, '  ');

结果:

{
  "name": "小明",
  "age": 14,
  "gender": true,
  "height": 1.65,
  "grade": null,
  "middle-school": "\"W3C\" Middle School",
  "skills": [
    "JavaScript",
    "Java",
    "Python",
    "Lisp"
  ]
}

第二个参数用于控制如何筛选对象的键值,如果只想输出指定的属性,可以穿入Array

JSON.stringify(xiaoming, ['name', 'skills'], '  ');

结果:

{
  "name": "小明",
  "skills": [
    "JavaScript",
    "Java",
    "Python",
    "Lisp"
  ]
}

还可以传入一个函数,这样对象的每个键值对都会被函数先处理:

function convert(key, value) {
    if (typeof value === 'string') {
        return value.toUpperCase();
    }
    return value;
}

JSON.stringify(xiaoming, convert, '  ');

上面代码把所有属性值变为大写:

{
  "name": "小明",
  "age": 14,
  "gender": true,
  "height": 1.65,
  "grade": null,
  "middle-school": "\"W3C\" MIDDLE SCHOOL",
  "skills": [
    "JAVASCRIPT",
    "JAVA",
    "PYTHON",
    "LISP"
  ]
}

JSON


阅读: 102315
JSON是JavaScript Object Notation的缩写,它是一种数据交换格式。

在JSON出现之前,大家一直用XML来传递数据。因为XML是一种纯文本格式,所以它适合在网络上交换数据。XML本身不算复杂,但是,加上DTD、XSD、XPath、XSLT等一大堆复杂的规范以后,任何正常的软件开发人员碰到XML都会感觉头大了,最后大家发现,即使你努力钻研几个月,也未必搞得清楚XML的规范。

终于,在2002年的一天,道格拉斯·克罗克福特(Douglas Crockford)同学为了拯救深陷水深火热同时又被某几个巨型软件企业长期愚弄的软件工程师,发明了JSON这种超轻量级的数据交换格式。

道格拉斯同学长期担任雅虎的高级架构师,自然钟情于JavaScript。他设计的JSON实际上是JavaScript的一个子集。在JSON中,一共就这么几种数据类型:

number:和JavaScript的number完全一致;
boolean:就是JavaScript的true或false;
string:就是JavaScript的string;
null:就是JavaScript的null;
array:就是JavaScript的Array表示方式——[];
object:就是JavaScript的{ … }表示方式。
以及上面的任意组合。

并且,JSON还定死了字符集必须是UTF-8,表示多语言就没有问题了。为了统一解析,JSON的字符串规定必须用双引号"",Object的键也必须用双引号""。

由于JSON非常简单,很快就风靡Web世界,并且成为ECMA标准。几乎所有编程语言都有解析JSON的库,而在JavaScript中,我们可以直接使用JSON,因为JavaScript内置了JSON的解析。

把任何JavaScript对象变成JSON,就是把这个对象序列化成一个JSON格式的字符串,这样才能够通过网络传递给其他计算机。

如果我们收到一个JSON格式的字符串,只需要把它反序列化成一个JavaScript对象,就可以在JavaScript中直接使用这个对象了。

- 序列化

让我们先把小明这个对象序列化成JSON格式的字符串:

‘use strict’;

var xiaoming = {
name: ‘小明’,
age: 14,
gender: true,
height: 1.65,
grade: null,
‘middle-school’: ‘“W3C” Middle School’,
skills: [‘JavaScript’, ‘Java’, ‘Python’, ‘Lisp’]
};

var s = JSON.stringify(xiaoming);
console.log(s);

Run
{“name”:“小明”,“age”:14,“gender”:true,“height”:1.65,“grade”:null,“middle-school”:"“W3C” Middle School",“skills”:[“JavaScript”,“Java”,“Python”,“Lisp”]}
要输出得好看一些,可以加上参数,按缩进输出:

JSON.stringify(xiaoming, null, ’ ');
结果:

{
“name”: “小明”,
“age”: 14,
“gender”: true,
“height”: 1.65,
“grade”: null,
“middle-school”: ““W3C” Middle School”,
“skills”: [
“JavaScript”,
“Java”,
“Python”,
“Lisp”
]
}
第二个参数用于控制如何筛选对象的键值,如果我们只想输出指定的属性,可以传入Array:

JSON.stringify(xiaoming, [‘name’, ‘skills’], ’ ');
结果:

{
“name”: “小明”,
“skills”: [
“JavaScript”,
“Java”,
“Python”,
“Lisp”
]
}
还可以传入一个函数,这样对象的每个键值对都会被函数先处理:

function convert(key, value) {
if (typeof value === ‘string’) {
return value.toUpperCase();
}
return value;
}

JSON.stringify(xiaoming, convert, ’ ');
上面的代码把所有属性值都变成大写:

{
“name”: “小明”,
“age”: 14,
“gender”: true,
“height”: 1.65,
“grade”: null,
“middle-school”: ““W3C” MIDDLE SCHOOL”,
“skills”: [
“JAVASCRIPT”,
“JAVA”,
“PYTHON”,
“LISP”
]
}
如果我们还想要精确控制如何序列化小明,可以给xiaoming定义一个**toJSON()**的方法,直接返回JSON应该序列化的数据:

var xiaoming = {
    name: '小明',
    age: 14,
    gender: true,
    height: 1.65,
    grade: null,
    'middle-school': '\"W3C\" Middle School',
    skills: ['JavaScript', 'Java', 'Python', 'Lisp'],
    toJSON: function () {
        return { // 只输出name和age,并且改变了key:
            'Name': this.name,
            'Age': this.age
        };
    }
};

JSON.stringify(xiaoming); // '{"Name":"小明","Age":14}'

- 反序列化

使用**JSON.parse()**反序列化JSON格式字符串为JS对象:

JSON.parse('[1,2,3,true]'); // [1, 2, 3, true]
JSON.parse('{"name":"小明","age":14}'); // Object {name: '小明', age: 14}
JSON.parse('true'); // true
JSON.parse('123.45'); // 123.45
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值