Date 的GMT、UTC、ISO、CST、timestamp 等格式 及Moment、Dayjs

一、不同的时间格式

1.1、时间的由来

一直被各种时间格式困扰,罗列常见的几种时间格式

new Date() // Fri Nov 25 2022 21:29:14 GMT+0800 (中国标准时间)
new Date().toISOString() // '2022-11-25T13:30:39.593Z'
new Date().toUTCString() // 'Fri, 25 Nov 2022 13:31:26 GMT'
new Date().valueOf() // 1669383136370

这些时间格式的解释
地球自转
众所周知,地球绕自转轴自西向东的转动,而太阳东起西落,因此,东时区的人会比西时区的人早一些看到太阳,从而时间上会早一点。
本初子午线
什么是本初子午线呢?
本初子午线,地球上的零度经线,经线指示南北方向,所有的经线长度相等,经线标注的度数就是经度。国际上将通过英国伦敦格林尼治天文台原址的那条经线称为0°经线,也叫本初子午线。
在这里插入图片描述
看一下这条著名的本初子午线
https://www.bilibili.com/video/BV1kC4y1h75h/?spm_id_from=333.337.search-card.all.click&vd_source=87a272335c14835b86c404606906248b
在这里插入图片描述

时区的划分:
以本初子午线为0°经线,左边是左半球,右边是右半球,共有24个时区,每个时区15°,每个时区间隔1个小时

中国所在的时区
在这里插入图片描述
全国的标准时间,都指的是北京时间(即东八区时间)

中国古代是怎么计时的

  1. 古代历法对年月日的定义

我国历法以月球绕地球一周的时间(29.5306天)为一月,以地球绕太阳一周的时间( 365.2419 天)为一年,为使一年的平均天数与回归年的天数相符,设置闰月。

中国古代一般采用的是阴历,阴历在天文学中主要指按月亮的月相周期来安排的历法,以月球绕行地球一周(以太阳为参照物,实际月球运行超过一周。)为一月,即以朔望月作为确定历月的基础,一年为十二个历月的一种历法。

在历法发展衍变过程中,出现了二十四节气,形成了农历(汉历)

立春、雨水、惊蛰、春分、清明、谷雨、
立夏、小满、芒种、夏至、小暑、大暑、
立秋、处暑、白露、秋分、寒露、霜降、
立冬、小雪、大雪、冬至、小寒、大寒

  1. 对年月日的计算

天干地支,是过去人建历法时,为了方便做 60 进位而设出的符号
历法用天干、地支编排年号和日期,天干共十个字「十干」,排列顺序为:
甲、乙、丙、丁、戊、己、庚、辛、壬、癸;
地支共十二个字,排列顺序为:
子、丑、寅、卯、辰、巳、午、未、申、酉、戌、亥。

甲、丙、戊、庚、壬为阳干; 乙、丁、己、辛、癸为阴干。
子、寅、辰、午、申、戌为阳支;丑、卯、巳、未、酉、亥为阴支

<规则>
一个干和一个地支相配,排列起来,天干在前,地支在后,天干由甲起,地支由子起,阳干对阳支,阴干对阴支(阳干不配阴支,阴干不配阳支)得到六十年一周期的甲子回圈。

年:
每个干支为一年,六十个干后,又从头算起,周而复始,循环不息。由甲子开始,满六十年称做一甲子或一花甲子。称为干支纪年法。
时:
由甲子时开始,但记时的地支固定不变,每天十二个时辰。(夜半二十三点至一点为子时,一至三点为丑时,三至五点为寅时,五点到七点为卯时,七点到九点为辰时,)

2022年11月29日 -> 农历:2022年11月初六,16点
壬寅年,辛亥月,丙戌日,未时

  1. 古代的计时工具

一、日晷(利用日影测时刻)
二、圭表(直立于平地上测日影的标杆和石柱,叫作表;正南正北方向平放的测定表影长度的刻板,叫作圭)
三、刻漏(漏刻是以壶盛水,利用水均衡滴漏原理,观测壶中刻箭上显示的数据来计算时间。)
四、沙漏(因漏刻冬天水易结冰,用流沙驱动漏刻。[明:五轮沙漏])

1.2、国际标准时间格式

1) 格林威治标准时间(GMT):
Tue, 29 Nov 2022 03:30:28 GMT // GMT 时间
Tue Nov 29 2022 11:30:48 GMT+0800 (中国标准时间) // 本地时间

「格林威治标准时间」(Greenwich Mean Time,简称G.M.T.)以伦敦格林威治的子午线为基线,以地球自转为标准,全球都以此标准设定时间。

2) 世界标准时(UTC):

由于地球每天的自转是有些不规则的,而且正在缓慢减速,也就是说有时候 24h 多一点转一圈,有时候还不到 24h 就转了一圈。
UTC 基于国际原子时间,通过不规则的加入闰秒来抵消地球自转变慢的影响,是世界上调节时钟和时间的主要时间标准。

在表示上,日期和时间中间有一个字母 T表示 UTC 时间
UTC +时区差=本地时间

Tue, 29 Nov 2022 03:28:59 GMT    // UTC时间
Tue Nov 29 2022 11:28:59 GMT+0800 (中国标准时间) // 本地时间

世界协调时(Coordinated Universal Time,简称UTC)又称世界标准时间或世界协调时间,是最主要的世界时间标准,在时刻上尽量接近于格林尼治标准时间。对于大多数用途来说,UTC时间被认为能与GMT时间互换,基本相等,但GMT时间已不再被科学界所确定

3) 中国标准时间(CST)
Fri Nov 25 2022 13:52:26 GMT+0800 (中国标准时间) // CST格式
new Date() // Fri Nov 25 2022 13:52:26 GMT+0800 (中国标准时间)

中国大陆、中国香港、中国澳门、中国台湾、蒙古国、新加坡、马来西亚、菲律宾、西澳大利亚州的时间与UTC的时差均为+8,也就是UTC+8

CST可以是美国中部时间,澳大利亚中部时间,古巴标准时间,中国标准时间。
建议不要使用CST时间,
对于以下时间,你可能不知道它到底是北京时间,还是其它时间:
Wed Aug 1408:21:05 CST 2013 / /北京、北美中部、古巴、澳洲中部

4) ISO 8601 标准时间

国际通用的无歧义的日期和时间格式

在 ISO 8601 的表示中,日期和时间按照这样的顺序排列:大的单位(比如年)放在左边,小的单位依次往右排列。表示只能由阿拉伯数字和指定的特殊字符(比如"-“, “:”, “T”, “W”, “Z”)等组成,这样的话,日常常用的描述性的单词(比如"January”, “Thursday”, or “New Year’s Day”)是不允许使用的。

2022-11-29T03:34:26.567Z // ISO 8601
2022-11-29T11:34:26.567Z+08:00 // 本地时间
// 字母T:分割日期和时间
// 而786表示的毫秒
// Z表示UTC统一时间
5) 时间戳

时间不分东西南北、在地球的每一个角落都是相同的。他们都有一个相同的名字,叫时间戳。
时间戳 指的就是Unix时间戳(Unix timestamp)。
定义为从格林威治时间 1970年01月01日00时00分00秒 起 至 现在 的总秒数。

new Date().valueOf() // 1669383136370

二、Date

创建日期对象,使用 new 操作符调用Date 构造函数,返回 Fri Nov 25 2022 21:29:14 GMT+0800 (中国标准时间) 这样的对象

new Date() // Fri Nov 25 2022 21:29:14 GMT+0800 (中国标准时间)(CST)

注:

new Date() 取到的是系统时间,也就是当前浏览器所在系统的的设置时间(包含时区)。

2.1、传参形式

1)参数是字符串类型

优点:传什么时间就是什么时间
缺点:如果传参超出有效范围 会返回无效日期

new Date("month dd,yyyy hh:mm:ss");
new Date("month dd,yyyy");
// 示例
new Date('2022,11,28,18:31:08') // Mon Nov 28 2022 18:31:08 GMT+0800 (中国标准时间)
new Date('2022,13,28,18:31:08') // Invalid Date

2)参数是数字类型

优点: 超出临界值(最小值 和 最大值) 会自动换算
缺点: 月份(0-11 需要自己计算)
传参时: 月份参数 = 期望的月份 - 1

new Date(year,?month,?day,?hours,?minutes,?seconds,?ms); // 参数对应(年,月,日,时,分,秒,毫秒)
// 示例
new Date(2022,11,28,18,31,08)  // Wed Dec 28 2022 18:31:08 GMT+0800 (中国标准时间)
new Date(2022,10,28,18,31,08) // Mon Nov 28 2022 18:31:08 GMT+0800 (中国标准时间)
new Date(2022,12,28) // Sat Jan 28 2023 00:00:00 GMT+0800 (中国标准时间)

3)参数是纯数字(时间戳)
参数表示的是需要创建的时间和GMT时间1970年1月1日之间相差的毫秒数

new Date(ms);
// 示例
new Date(0) // Thu Jan 01 1970 08:00:00 GMT+0800 (中国标准时间)
new Date(1669631641571) // Mon Nov 28 2022 18:34:01 GMT+0800 (中国标准时间)

4)以一个日期对象做参数

var date = new Date();
new Date(date);  // 返回当前时间

2.2、获取时间戳的函数

1)Date.now()

语法:无参数,返回自1970年1月1日 00:00:00 UTC到当前时间的毫秒数

Date.now();
2)Date.parse()

语法:参数是必传的,符合 ISO 8601 日期格式的字符串;返回自1970年1月1日 00:00:00 UTC到当前时间的毫秒数

Date.parse( '2022-5-4 12:23:33' )   // 1651638213000
3) Date.UTC()

语法:参数是必传的,符合期构造函数参数,返回自1970年1月1日 00:00:00 UTC到当前时间的毫秒数

Date.UTC(year,month,?day,?hours,?minutes,?seconds,?ms)
Date.UTC(2022,11,27)  // 1672099200000

2.3、日期格式化方法

这 7 种方法专门用于格式化日期时间,都返回字符串

方法说明示例
toDateString()显示周几、月、日、年‘Fri Nov 25 2022’
toTimeString()显示日期中的时、分、秒和时区‘21:51:53 GMT+0800 (中国标准时间)’
toLocaleDateString()显示日期中的年月日‘2022/11/25’
toLocaleTimeString()显示日期中的时分秒‘21:57:18’
toUTCString()显示完整UTC时间‘Fri, 25 Nov 2022 13:57:36 GMT’
toGMTString()显示完整GMT时间,和UTC时间一致‘Fri, 25 Nov 2022 13:59:23 GMT’
toISOString()显示完整的ISO时间‘2022-11-25T13:30:39.593Z’
new Date().toDateString() // 'Fri Nov 25 2022'
new Date().toTimeString() // '21:51:53 GMT+0800 (中国标准时间)'
new Date().toLocaleDateString() // '2022/11/25'
new Date().toLocaleTimeString() // '21:57:18'
new Date().toUTCString() // 'Fri, 25 Nov 2022 13:57:36 GMT'
new Date().toGMTString()  // 'Fri, 25 Nov 2022 13:59:23 GMT'
new Date().toISOString() // '2022-11-25T13:30:39.593Z'

// toLocaleString方法
new Date().toLocaleString() // '2022/11/28 18:21:16'

2.4、日期/时间组件方法

方法说明
getTime()返回时间戳
getFullYear()返回4位数(2022)
getMonth()返回日期的月(0:1月~~~ 11:12月)
getDate()返回日期的日(1-31)
getDay()返回日期的周几(0:周日;6:周六)
getHours()返回日期的时(0~23)
getMinutes()返回日期的分(0~59)
getSeconds()返回日期的秒(0~59)
getMillseconds()返回日期的毫秒

2.5、不同格式间的转换

1)任意时间 -> CST

const time = 1531065600000//时间戳(数字)
const youData = new Data(time);

1new Date(“month dd,yyyy hh:mm:ss”);
2new Date(“month dd,yyyy”);
3new Date(yyyy,mth,dd,hh,mm,ss); //注意:这种方式下,必须传递整型;
4new Date(yyyy,mth,dd);
5new Date(ms); 

2)时间戳 / CST -> yyyy-MM-dd HH-mm-ss

function timestampToTime(timestamp) {
 // var date = new Date(d); // 传入时间是CST
  var date = new Date(timestamp * 1000);//时间戳为10位需*1000,时间戳为13位的话不需乘1000
  var Y = date.getFullYear() + '-';
  var M = (date.getMonth()+1 < 10 ? '0'+(date.getMonth()+1):date.getMonth()+1) + '-';
  var D = (date.getDate()< 10 ? '0'+date.getDate():date.getDate())+ ' ';
  var h = (date.getHours() < 10 ? '0'+date.getHours():date.getHours())+ ':';
  var m = (date.getMinutes() < 10 ? '0'+date.getMinutes():date.getMinutes()) + ':';
  var s = date.getSeconds() < 10 ? '0'+date.getSeconds():date.getSeconds();
  return Y+M+D+h+m+s;
}

注意:date.getMonth() 得到的月是从0开始的,date 所有的 get 方法除了 date.getFullYear() 得到的是四位数年份,其余的 get 方法得到的数若小于 10,都是以单数出现,若要得到两位的自己拼接0

3)获取当前时间戳的方法

// 方法一,Date.UTC()
Date.UTC(2022,10,29,16,00,00,000)   // 1669737600000
// 方法二,使用 '+' 号,推荐!!!
+ new Date()   // 输出当前时间戳
//一元运算 '+' 会触发 valueOf 方法作用到 Date 对象上,会直接返回时间戳
// 方法三
new Date().getTime(); // 输出当前时间戳
// 方法四
Date.now() / 1000  // 不包括毫秒
// 方法五
new Date().valueOf() // 输出当前时间戳
// 方法六
Date.parse(2022,11,28)

示例

var stringTime = '2022-10-12 22:37:33';
//将获取到的时间转换成时间戳
var timestamp = Date.parse(new Date(stringTime));

4)获取一天前,一月前的方法

function date(){
   var date = new Date();
   var oneDate = 1
   var dateMid = date.getTime() - (oneDate * 24 * 60 * 60 * 1000)
   var dateBefore = new Date(dateMid); // 距当前时间一天前的CST
   return dateBefore 
}

三、moment.js

star:44k
文档:https://momentjs.com/
GitHub地址:https://github.com/moment/moment

Moment.js 是一个 JavaScript 日期处理类库(处理时间格式化的npm包),用于解析、检验、操作、以及显示日期

优点:

不依赖任何第三方库
支持字符串、Date、时间戳以及数组等格式
浏览器和 node 环境中都可以使用
前后端通用,文档详细

moment 接收的参数
在这里插入图片描述

3.1、常用函数

1)format
时间格式化,将时间输出入你想要的时间的格式

moment().format() // 2022-11-28T12:23:26+08:00
moment().format('YYYY-MMM-DD') // 2022-Nov-29
moment().format('YYYY.MM.DD HH:mm:ss') // 2022.11.28 12:24:06
moment().format('HH时mm分ss秒')   //24小时制
moment().format('hh:mm:ss a')   // 12小时制
moment(时间戳).format("YYYY-MM-DD")   //输出实例 如 2022-11-28
// 示例
moment().format()  // 2022-11-28T22:21:52+08:00

2)year、month、day、hour、minute、second、millisecond

var t = moment().format()  // 2022-11-28T20:50:05+08:00
moment(t).year(); // 2022
moment(t).month() + 1; // 11
moment(t).date(); // 28
moment(t).hour(); // 20
moment(t).minute(); // 50
moment(t).second(); // 5
moment(t).millisecond(); // 0

注:
month函数

month函数中,月份为0到11之间的数字,超出这个数字范围则冒泡到年份。
month函数传入数值是number类型数字,代表设置;
如果不传入,代表获取,返回值也是number类型的

year函数

year函数获取传入时间的年份或者设置年份,年份是-270000到270000之间number类型的数字。
不传值为获取,返回值是年份,number类型的数字;
传值代表设置年份,传入number类型的数字

3)week 与 quarter

week函数获取所在年的周数或者设置周数(星期数)
传入值代表设置,传入值的类型是number类型的数字;
不传值代表获取,返回值是number类型的数字

quarter函数获取传入时间的季度或者设置季度,季度为1-4之间的数字,
quarter函数传入数值都是number类型的数字;
如果不传入,返回值也是number类型的数字

var t = moment().format()  // 2022-11-28T20:50:05+08:00
moment(time).week() // 49
moment(time).quarter() // 4

4) startOf 与 endOf

作用

顾名思义 ,以什么开始,以什么结尾,用来获取任意日期的任意精确值。
例如:获取今天精确到小时的日期、精确到秒的日期等等类似的情况

语法:string 可以是 year、month、quarter、week、day、hour、minute、second 等等

  moment().startOf(string);
  moment().endOf(string);

示例

// startOf
moment().startOf('month') // Tue Nov 01 2022 00:00:00 GMT+0800 (中国标准时间)
moment().startOf('week') // Sun Nov 27 2022 00:00:00 GMT+0800 (中国标准时间)
moment().startOf('day')  // Mon Nov 28 2022 00:00:00 GMT+0800 (中国标准时间) 
// endOf
moment().endOf('month')  // Wed Nov 30 2022 23:59:59 GMT+0800 (中国标准时间)
moment().endOf('week') // Sat Dec 03 2022 23:59:59 GMT+0800 (中国标准时间)
moment().endOf('day') // Mon Nov 28 2022 23:59:59 GMT+0800 (中国标准时间)

解析:

  • startOf 为获取指定参数的起始时间,例如:moment().startOf(‘hour’);
    获取的就是今天准确的小时的第一分钟,除了小时,其余参数用00补齐
  • endOf 为获取指定参数的结束时间,例如:moment().startOf(‘hour’);
    获取的就是今天准确的小时的最后一分钟,除了小时,其余参数用59补齐

5) valueOf

valueOf 输出自 Unix 纪元以来的毫秒数,和 date.valueOf 一样

moment().valueOf() // 1669648642597
+moment(1669648642597); // 1669648642597

6) subtract 与 add
add():通过增加时间来改变原始的 moment
语法

moment().add(Number, String); 
moment().add(Duration); 
moment().add(Object);

示例

moment().add(2,'months').date(0) // 未来一个月的最后一天
moment().add(1, "months").format("YYYY-MM-DD HH:mm:ss.sss") // 下个月
moment().add(1, "week").format("YYYY-MM-DD HH:mm:ss.sss") // 下一周
moment().add(1, "day").format("YYYY-MM-DD HH:mm:ss.sss") // 明天
moment().add(7, "d").format() // Tue Dec 06 2022 14:10:46 GMT+0800 (中国标准时间)

subtract():与 add() 完全相同,减去对应的时间

moment().subtract(1,’months’).date(1) // 上个月第一天
moment().subtract(1, "months").format("YYYY-MM-DD HH:mm:ss.sss") // 上个月
moment().subtract(1, "week").format("YYYY-MM-DD HH:mm:ss.sss") // 上周
moment().subtract(1, "day").format("YYYY-MM-DD HH:mm:ss.sss") // 昨天

String 可简写

快捷键
yearsy
quartersQ
monthsM
weeksw
daysd
hoursh
minutesm
secondss
millisecondsms

3.2、常用格式间的转换

1) CST -> 时间戳

moment().format('X') // (大写X)以秒为单位,返回值为字符串类型
moment().format('x') // (小写x)以毫秒为单位,返回值为字符串类型
moment().valueOf()   //   以毫秒为单位,返回值为数值型

示例

moment().format('X') // 1669703058 (10位数的时间戳,精确到秒)
moment().format('x') // 1669703058284 (13位数的时间戳,精确到豪秒)

2) 时间戳 -> 正常时间

moment(1630512000000).format('YYYY-MM-DD HH:mm:ss')

3) 比较两个日期的大小

moment(end).diff(moment(start), 'seconds')
moment(1730512000000).diff(moment(1630512000000), 'y') // 3

四、day.js

star:27.1k
官网:https://day.js.org/
GitHub地址:https://github.com/iamkun/dayjs

基本用法与 moment 相似

dayjs() // Tue Nov 29 2022 14:39:52 GMT+0800 (中国标准时间)

传入值是:ISO 8601时间字符串、Javascript Date 对象、Unix 时间戳 (13 位数字)

4.1、常用函数

1)获取与设置的函数 year()、month()、

示例

dayjs().year() // 2020
dayjs().year(2020)
dayjs().set('year',2020) // 2020

其它的日期/星期/时/分/秒等,参照下表

单位缩写详情
dateD月份里的星期
dayd星期几(星期天0,星期六6)
monthM月份(一月0,十二月11)
yeary年份
hourh小时
minutem分钟
seconds
millisecondms毫秒

2)add()与subtract()
增加时间并返回一个新的 Dayjs() 对象

dayjs().add(value : Number, unit : String);
dayjs().add(7, 'day'); //在当前的基础上加7天

减少时间并返回一个新的 Dayjs() 对象

dayjs().subtract(value : Number, unit : String);
dayjs().subtract(7, 'day'); //在当前基础上减少7天

3)startOf()与endOf()
返回当前时间的开头时间的 Dayjs() 对象,如月份的第一天

dayjs().startOf(unit : String);
dayjs().startOf('month'); 

返回当前时间的末尾时间的 Dayjs() 对象,如月份的最后一天

dayjs().endOf(unit : String);
dayjs().endOf('month');

4.2、dayjs的优势

  1. 和Moment.js有着相同的API和模式
  2. 不可变、持久性
  3. 提供链式调用
  4. 国际化标准
  5. 超小的压缩体积,仅仅有2kb左右(Moment.js压缩后大概有16.7k的样子)
  6. 极大多数的浏览器兼容
  • 16
    点赞
  • 24
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值