首页 > 其他分享 >Golang time包

Golang time包

时间:2024-07-16 18:29:48浏览次数:16  
标签:22 fmt Golang 时间 time Println now

time包

时间和日期是我们编程中经常会用到的,本文主要介绍了 Go 语言内置的 time 包的基本用法。time 包提供了一些关于时间显示和测量用的函数。time 包中日历的计算采用的是公历,不考虑润秒。

时间类型

Go 语言中使用time.Time类型表示时间。我们可以通过time.Now函数获取当前的时间对象,然后从时间对象中可以获取到年、月、日、时、分、秒等信息。

// timeDemo 时间对象的年月日时分秒
func timeDemo() {
	now := time.Now() // 获取当前时间
	fmt.Printf("current time:%v\n", now)

	year := now.Year()     // 年
	month := now.Month()   // 月
	day := now.Day()       // 日
	hour := now.Hour()     // 小时
	minute := now.Minute() // 分钟
	second := now.Second() // 秒
	fmt.Println(year, month, day, hour, minute, second)
}

Location和time zone

Go 语言中使用 location 来映射具体的时区。时区(Time Zone)是根据世界各国家与地区不同的经度而划分的时间定义,全球共分为24个时区。中国差不多跨5个时区,但为了使用方便只用东八时区的标准时即北京时间为准。

下面的示例代码中使用beijing来表示东八区8小时的偏移量,其中time.FixedZonetime.LoadLocation`这两个函数则是用来获取location信息。

// timezoneDemo 时区示例
func timezoneDemo() {
	// 中国没有夏令时,使用一个固定的8小时的UTC时差。
	// 对于很多其他国家需要考虑夏令时。
	secondsEastOfUTC := int((8 * time.Hour).Seconds())
	// FixedZone 返回始终使用给定区域名称和偏移量(UTC 以东秒)的 Location。
	beijing := time.FixedZone("Beijing Time", secondsEastOfUTC)

	// 如果当前系统有时区数据库,则可以加载一个位置得到对应的时区
	// 例如,加载纽约所在的时区
	newYork, err := time.LoadLocation("America/New_York") // UTC-05:00
	if err != nil {
		fmt.Println("load America/New_York location failed", err)
		return
	}
	fmt.Println()
	// 加载上海所在的时区
	//shanghai, err := time.LoadLocation("Asia/Shanghai") // UTC+08:00
	// 加载东京所在的时区
	//tokyo, err := time.LoadLocation("Asia/Tokyo") // UTC+09:00

	// 创建时间对象需要指定位置。常用的位置是 time.Local(当地时间) 和 time.UTC(UTC时间)。
	//timeInLocal := time.Date(2009, 1, 1, 20, 0, 0, 0, time.Local)  // 系统本地时间
	timeInUTC := time.Date(2009, 1, 1, 12, 0, 0, 0, time.UTC)
	sameTimeInBeijing := time.Date(2009, 1, 1, 20, 0, 0, 0, beijing)
	sameTimeInNewYork := time.Date(2009, 1, 1, 7, 0, 0, 0, newYork)

	// 北京时间(东八区)比UTC早8小时,所以上面两个时间看似差了8小时,但表示的是同一个时间
	timesAreEqual := timeInUTC.Equal(sameTimeInBeijing)
	fmt.Println(timesAreEqual)

	// 纽约(西五区)比UTC晚5小时,所以上面两个时间看似差了5小时,但表示的是同一个时间
	timesAreEqual = timeInUTC.Equal(sameTimeInNewYork)
	fmt.Println(timesAreEqual)
}

在日常编码过程中使用时间对象的时候一定要注意其时区信息。

Unix Time

Unix Time是自1970年1月1日 00:00:00 UTC 至当前时间经过的总秒数。下面的代码片段演示了如何基于时间对象获取到Unix 时间。

// timestampDemo 时间戳
func timestampDemo() {
	now := time.Now()        // 获取当前时间
	timestamp := now.Unix()  // 秒级时间戳
	milli := now.UnixMilli() // 毫秒时间戳 Go1.17+
	micro := now.UnixMicro() // 微秒时间戳 Go1.17+
	nano := now.UnixNano()   // 纳秒时间戳
	fmt.Println(timestamp, milli, micro, nano)
}

time 包还提供了一系列将 int64 类型的时间戳转换为时间对象的方法。

// timestamp2Time 将时间戳转为时间对象
func timestamp2Time() {
	// 获取北京时间所在的东八区时区对象
	secondsEastOfUTC := int((8 * time.Hour).Seconds())
	beijing := time.FixedZone("Beijing Time", secondsEastOfUTC)

	// 北京时间 2022-02-22 22:22:22.000000022 +0800 CST
	t := time.Date(2022, 02, 22, 22, 22, 22, 22, beijing)

	var (
		sec  = t.Unix()
		msec = t.UnixMilli()
		usec = t.UnixMicro()
	)

	// 将秒级时间戳转为时间对象(第二个参数为不足1秒的纳秒数)
	timeObj := time.Unix(sec, 22)
	fmt.Println(timeObj)           // 2022-02-22 22:22:22.000000022 +0800 CST
	timeObj = time.UnixMilli(msec) // 毫秒级时间戳转为时间对象
	fmt.Println(timeObj)           // 2022-02-22 22:22:22 +0800 CST
	timeObj = time.UnixMicro(usec) // 微秒级时间戳转为时间对象
	fmt.Println(timeObj)           // 2022-02-22 22:22:22 +0800 CST
}

时间间隔

time.Durationtime包定义的一个类型,它代表两个时间点之间经过的时间,以纳秒为单位。time.Duration表示一段时间间隔,可表示的最长时间段大约290年。

time 包中定义的时间间隔类型的常量如下:

const (
    Nanosecond  Duration = 1
    Microsecond          = 1000 * Nanosecond
    Millisecond          = 1000 * Microsecond
    Second               = 1000 * Millisecond
    Minute               = 60 * Second
    Hour                 = 60 * Minute
)

例如:time.Duration表示1纳秒,time.Second表示1秒。

时间操作

Add

Go语言的时间对象有提供Add方法如下:

func (t Time) Add(d Duration) Time

举个例子,求一个小时之后的时间:

func main() {
	now := time.Now()
	later := now.Add(time.Hour) // 当前时间加1小时后的时间
	fmt.Println(later)
}

Sub

求两个时间之间的差值:

func (t Time) Sub(u Time) Duration

返回一个时间段t-u。如果结果超出了Duration可以表示的最大值/最小值,将返回最大值/最小值。要获取时间点t-d(d为Duration),可以使用t.Add(-d)。

Equal

func (t Time) Equal(u Time) bool

判断两个时间是否相同,会考虑时区的影响,因此不同时区标准的时间也可以正确比较。本方法和用t==u不同,这种方法还会比较地点和时区信息。

Before

func (t Time) Before(u Time) bool

如果t代表的时间点在u之前,返回真;否则返回假。

After

func (t Time) After(u Time) bool

如果t代表的时间点在u之后,返回真;否则返回假。

定时器

使用time.Tick(时间间隔)来设置定时器,定时器的本质上是一个通道(channel)。

func tickDemo() {
	ticker := time.Tick(time.Second) //定义一个1秒间隔的定时器
	for i := range ticker {
		fmt.Println(i)//每秒都会执行的任务
	}
}

时间格式化

time.Format函数能够将一个时间对象格式化输出为指定布局的文本表示形式,需要注意的是 Go 语言中时间格式化的布局不是常见的Y-m-d H:M:S,而是使用 2006-01-02 15:04:05.000(记忆口诀为2006 1 2 3 4 5)。

其中:

  • 2006:年(Y)
  • 01:月(m)
  • 02:日(d)
  • 15:时(H)
  • 04:分(M)
  • 05:秒(S)

补充

  • 如果想格式化为12小时格式,需在格式化布局中添加PM
  • 小数部分想保留指定位数就写0,如果想省略末尾可能的0就写 9。
// formatDemo 时间格式化
func formatDemo() {
	now := time.Now()
	// 格式化的模板为 2006-01-02 15:04:05

	// 24小时制
	fmt.Println(now.Format("2006-01-02 15:04:05.000 Mon Jan"))
	// 12小时制
	fmt.Println(now.Format("2006-01-02 03:04:05.000 PM Mon Jan"))

	// 小数点后写0,因为有3个0所以格式化输出的结果也保留3位小数
	fmt.Println(now.Format("2006/01/02 15:04:05.000")) // 2022/02/27 00:10:42.960
	// 小数点后写9,会省略末尾可能出现的0
	fmt.Println(now.Format("2006/01/02 15:04:05.999")) // 2022/02/27 00:10:42.96

	// 只格式化时分秒部分
	fmt.Println(now.Format("15:04:05"))
	// 只格式化日期部分
	fmt.Println(now.Format("2006.01.02"))
}

解析字符串格式的时间

对于从文本的时间表示中解析出时间对象,time包中提供了time.Parsetime.ParseInLocation两个函数。

其中time.Parse在解析时不需要额外指定时区信息。

// parseDemo 指定时区解析时间
func parseDemo() {
	// 在没有时区指示符的情况下,time.Parse 返回UTC时间
	timeObj, err := time.Parse("2006/01/02 15:04:05", "2022/10/05 11:25:20")
	if err != nil {
		fmt.Println(err)
		return
	}
	fmt.Println(timeObj) // 2022-10-05 11:25:20 +0000 UTC

	// 在有时区指示符的情况下,time.Parse 返回对应时区的时间表示
	// RFC3339     = "2006-01-02T15:04:05Z07:00"
	timeObj, err = time.Parse(time.RFC3339, "2022-10-05T11:25:20+08:00")
	if err != nil {
		fmt.Println(err)
		return
	}
	fmt.Println(timeObj) // 2022-10-05 11:25:20 +0800 CST
}

time.ParseInLocation函数需要在解析时额外指定时区信息。

// parseDemo 解析时间
func parseDemo() {
	now := time.Now()
	fmt.Println(now)
	// 加载时区
	loc, err := time.LoadLocation("Asia/Shanghai")
	if err != nil {
		fmt.Println(err)
		return
	}
	// 按照指定时区和指定格式解析字符串时间
	timeObj, err := time.ParseInLocation("2006/01/02 15:04:05", "2022/10/05 11:25:20", loc)
	if err != nil {
		fmt.Println(err)
		return
	}
	fmt.Println(timeObj)
	fmt.Println(timeObj.Sub(now))
}

标签:22,fmt,Golang,时间,time,Println,now
From: https://blog.csdn.net/gopher9511/article/details/140473571

相关文章

  • AvalonMM接口Interval Timer IP的寄存器介绍和Interval Timer寄存器读写操作详解
    一、间隔定时器结构间隔定时器的结构框图: 该间隔定时器有如下两个特点:-Avalon-MM接口,提供对6个16位寄存器的访问;-有一个脉冲输出接口(可选),可用作周期性脉冲发生器;该间隔定时器的所有寄存器都是16位的,可兼容16-bit和32-bit处理器。某些寄存器只存在于特定的配置中,例如,当该......
  • golang使用yaml文件做配置文件
    yaml配置文件host:localhost:3306user:rootpwd:112233dbname:1安装yaml读取工具gogetgopkg.in/yaml.v2从yaml文件读取配置packagemain​import("fmt""gopkg.in/yaml.v2""os")​typeConfstruct{Host string`yaml:"host&qu......
  • golang IO流
    golangIO流file一些操作os包下FileInfo:获取文件信息Reader:读Write:写文件复制mkdircreateremoveSeeker接口设置光标的位置,读写文件typeSeekerinterface{//1、offset偏移量3//2、whence如何设置,当前光标的位置。Seek(offsetint64,whence......
  • java mapstruct 同字段LocalDateTime和LocalDate不同类型转换处理
    解决方式:在接口中定义方法传入参数、返回参数为对一个的类型,mapstruct的实现类会自动调用该方法。代码:@Mapper(builder=@Builder(disableBuilder=true))publicinterfaceStlmtCheckingResultConvert{StlmtCheckingResultConvertINSTANCE=Mappers.getMapper(Stl......
  • 修复《NBA 2K23》“vcruntime140.dll“ 缺失:全面恢复指南
    在尝试运行备受期待的篮球模拟游戏《NBA2K23》时,不少玩家遇到了一个令人沮丧的问题:“vcruntime140.dll”文件丢失。这个动态链接库(DLL)文件是VisualC++Redistributable的一部分,对于许多基于Windows的应用程序来说至关重要。本文将指导你如何快速、有效地解决这个问题,让你能够......
  • onnxruntime无法使用GPU加速 加速失败 解决方法【非常详细】
    onnx无法使用GPU加速加速失败解决方法【非常详细】 应该是自目前以来最详细的加速失败解决方法GPU加速,收集了各方的资料。引用资料见后文硬件配置:GPUCUDA版本:12.2客户架构:window10输入: nvcc--version onnxruntime版本后文提供1先检测是否无法使用GPU加速检测......
  • 紧急手撸 console.time()
    前要最近做需求开发想要看一下代码块的运行耗时,无意间看到了console.time()、console.timeEnd(),出于好奇就深入了解了一下原理没啥好说的,我们来看看怎么手撸一个console.time()最初是想着简简单单使用个newDate()来记录运行耗时的,谁知道后面...我们来简单请出我......
  • TimescaleDB时间序列数据库
    TimescaleDB:这是一款支持完整sql开源的时间序列数据库。用处1、数据量庞大2、只做时间索引类的插入3、很少更新数据TimescaleDB的好处:基于时序优化自动分片(自动按时间、空间分片(chunk))全SQL接口支持垂直于横向扩展支持时间维度、空间维度自动分区。空间维度指属性字......
  • golang的一些体会
     1.接口变量肯定对应一种具体类型,参考java的接口与实现。2.如果使用接口类型变量存储对象,那内存里会存两份内容:实际类型、接口类型(含接口中的函数指针列表)。   -其实这里的函数指针列表类似于C++的虚函数表。   -因为go的鸭子类型,所以接口变量必须记录接口中函数......
  • Golang - 使用责任链模式代替IF ELSE
    一、传统IF判断1、在业务中使用大量的if判断代码如下:packagemaintypeSellInfostruct{Pricefloat64OrderCountintTotalCountintMemberShipint}funcmain2(){vara=SellInfo{Price:1.0,OrderCount:......