为什么要写处理时间的包
开发中,关于处理时间转换虽然是一件不值一提很微不足道很小的事情,但也是一个常见的事情。
封装的不好的时间操作工具库,造成每次调用麻烦,
例如要调用不同的函数来处理 时间戳 时间字符串 时间对象之间的转换,
以及烦人的时区的转化,可能从一个时间种类变化到另一个时间类型形态,用户在中间过程要调用三四次不同的函数来转化,
才能处理得到想要的最终结果。
NbTime对象实例化入参接受所有种类的入参,不需要用户针对不同的传参类型做时间转化而选择不同的函数
,用户无脑将任意入参传给NbTime即可;NbTime将常用的时间处理转化结果,作为对象的惰性属性。
一个NbTime的实例化入参搞定所有时间转化需求,不需要用户亲自去选择各种用途的时间转换函数来对时间做转换。
例如像下面图片这种 模块级 + 各种各样的函数 封装的 时间工具包,就太不好用了,因为需要记忆和选择各种各样的不同用途的函数对时间进行转化。
封装时间操作不难,但如果封装的不好用,造成项目中调用它处处难。
那种 一个 time_utils.py 下 def 100 多个时间转换函数的 公共工具包,真的太难用了,用的时候都不知道选用什么函数好。
NbTime 是oop面向对象开发的爽快的日期时间操作类
NbTime 支持无限链式操作来处理时间,
(因为是oop所以易用程度远远的暴击面向过程python工程师写的time_utils.py里面
写几百个独立的操作时间的面向过程函数)
NbTime 入参支持 None 字符串 时间戳 datetime对象 NbTime对象自身
NbTime 支持将任意格式的时间字符串转成时间对象,无需提前精确指定写 yyyyy-mm-dd HHMMSS 这样的模板。
NbTime 非常轻松支持时区转化
Nbtime 内置属性 datetime对象,兼容性好
NbTime操作时间,远远暴击使用datetime和三方arrow包,
远远暴击用户在 utils.time_utils.py文件中写几百个孤立的面向过程操作时间的函数.
pip install nb_time
NbTime 最方便的地方在于入参可以是任何种类,可以不传参;可以传递数字时间戳,自动识别是否是毫秒时间戳;
可以传递datetime对象;可以传递NbTime类型的对象;
可以传递时间字符串,而且可以自动把任何格式模板的时间字符串自动转化成NbTime对象;
综上所述NbTime入参方式已经囊括了所有可能。
所以用户始终用NbTime就可以了,无需记忆和选择几百个各种各样的时间转换函数。
不管是从 时间戳 时间字符串 datetime对象 以及不同时区 的之间互相转化,都是使用 NbTime 对象作为中转对象。
>>> from nb_time import NbTime
>>> NbTime()
<NbTime [2024-02-29 17:51:14 +0800]>
>>> NbTime(datetime.datetime.now())
<NbTime [2024-02-29 17:56:43 +0800]>
>>> NbTime(1709192429)
<NbTime [2024-02-29 15:40:29 +0800]>
传了大于13位的毫秒时间戳,也能自动转化。
>>> NbTime(1709192429000)
<NbTime [2024-02-29 15:40:29 +0800]>
>>> NbTime('2024-02-26 15:58:21',datetime_formatter=NbTime.FORMATTER_DATETIME,time_zone=NbTime.TIMEZONE_EASTERN_7).to_tz('UTC+8')
<NbTime [2024-02-26 16:58:21 +0800]>
Nbtime 万能自动识别时间字符串模板,可以将所有常见的时间字符串转换成时间对象,不需要提前精确的写 yyyy-mm-dd 这样的。
以下例子都能直接转化成时间对象,无视时间字符串格式。
from nb_time import NbTime
print(NbTime('20230506T010203.886 +08:00'))
print(NbTime('2023-05-06 01:02:03.886'))
print(NbTime('2023-05-06T01:02:03.886 +08:00'))
print(NbTime('20221206 1:2:3'))
print(NbTime('Fri Jul 19 06:38:27 2024'))
print(NbTime('2013-05-05 12:30:45 America/Chicago'))
>>> from nb_time import DateTimeValue
>>> NbTime(DateTimeValue(year=2022,month=5,day=9,hour=6),time_zone='UTC+7')
<NbTime [2022-05-09 06:00:00 +0700]>
NbTime入参本身支持无限嵌套NbTime对象
NbTime(NbTime(NbTime(NbTime())))
<NbTime [2024-02-29 18:39:09]>
为什么 NbTime支持入参是自身类型,例如你可以方便的转时区和转字符串格式化
例如0时区的2024-02-29 07:40:34,你要转化成8时区的带毫秒带时区的时间字符串,
>>> from nb_time import NbTime
>>> NbTime(NbTime('2024-02-29 07:40:34', time_zone='UTC+0', datetime_formatter=NbTime.FORMATTER_DATETIME_NO_ZONE),
... time_zone='UTC+8', datetime_formatter=NbTime.FORMATTER_MILLISECOND).datetime_str
'2024-02-29 15:40:34.000000 +0800'
NbTime().shift方法返回的对象仍然是Nbtime类型。 因为Nbtime对象本身具有很多好用的属性和方法,所以使用NbTime作为时间转化的中转对象,比使用datetime作为中转对象方便使用很多。
求3天1小时10分钟后的时间,入参支持正数和负数
>>> NbTime().shift(hours=1,minutes=10).shift(days=3)
<NbTime [2024-03-03 19:02:49 +0800]>
求当前时间1天之前的时间戳
>>> NbTime().shift(days=-1).timestamp
1709290123.409756
实例化时候分别设置东7区和0时区
>>> NbTime(time_zone='UTC+7')
<NbTime [2024-02-29 17:05:08 +0700]>
>>> NbTime(time_zone='UTC+0')
<NbTime [2024-02-29 10:05:08 +0000]>
用户不传递时区时候,默认就是操作系统时区,如果用户想统一设置时区
例如用户统一设置东8区,以后实例化就不用每次亲自传递东八区.
NbTime.set_default_time_zone('UTC+8')
用户不想要毫秒时间字符串
>>> NbTime(datetime_formatter=NbTime.FORMATTER_DATETIME)
<NbTime [2024-02-29 18:10:57 +0800]>
用户不想要字符串带时区
>>> NbTime(datetime_formatter=NbTime.FORMATTER_DATETIME_NO_ZONE)
<NbTime [2024-02-29 18:12:18]>
NbTime.set_default_formatter 可以全局设置时间格式字符串,就不需要每次都传递格式
>>> NbTime.set_default_formatter(NbTime.FORMATTER_DATETIME_NO_ZONE)
>>> NbTime()
<NbTime [2024-02-29 18:14:38]>
见下面的交互,NbTime类型对象有非常便捷的各种成员变量,
datetime 类型datetime.datetime类型的时间对象,这个很方便和内置类型关联起来
time_zone_obj 时区
datetime_str 日期时间字符串
time_str 时间字符串
date_str 日期字符串
timestamp 时间戳秒
timestamp_millisecond 时间戳毫秒
today_zero_timestamp 当天凌晨的时间戳
>>> nbt=NbTime()
>>> nbt.datetime
datetime.datetime(2024, 2, 29, 18, 16, 23, 541415, tzinfo=<DstTzInfo 'Asia/Shanghai' CST+8:00:00 STD>)
>>> nbt.time_zone_obj
<DstTzInfo 'Asia/Shanghai' LMT+8:06:00 STD>
>>> nbt.datetime_str
'2024-02-29 18:16:23'
>>> nbt.time_str
'18:16:23'
>>> nbt.date_str
'2024-02-29'
>>> nbt.timestamp
1709201783.541415
>>> nbt.timestamp_millisecond
1709201783541.415
>>> nbt.today_zero_timestamp
1709136000
例如获取今天的年月日,中间不要带 -
>>> NbTime().get_str('%Y%m%d')
20240301
求3天1小时10分钟后的时间,入参支持正数和负数
>>> NbTime().shift(hours=1,minutes=10).shift(days=3)
<NbTime [2024-03-03 19:02:49 +0800]>
一个东7区的时间:
>>> NbTime('2024-02-26 15:58:21',datetime_formatter=NbTime.FORMATTER_DATETIME,time_zone=NbTime.TIMEZONE_EASTERN_7)
<NbTime [2024-02-26 15:58:21 +0700]>
那这个东7区的时间转化成东8区的时间:
>>> NbTime('2024-02-26 15:58:21',datetime_formatter=NbTime.FORMATTER_DATETIME,time_zone=NbTime.TIMEZONE_EASTERN_7).to_tz('UTC+8')
<NbTime [2024-02-26 16:58:21 +0800]>
例如东7区的2024-02-29 07:40:34转成东八区的时间字符串。
from nb_time import NbTime
# NbTime对象无限嵌套传参给NbTime方式
print(NbTime(NbTime('2024-02-29 07:40:34', time_zone='UTC+7'), time_zone='UTC+8').datetime_str)
# to_tz 方式
print(NbTime('2024-02-29 07:40:34', time_zone='UTC+7').to_tz('UTC+8').datetime_str)
NbTime 实现了 __gt__ __lt__ __eq__ 方法,可以直接比较大小
>>> NbTime() > NbTime('2023-05-06 01:01:01')
True
>>> NbTime() > NbTime('2025-05-06 01:01:01')
False
因为 nb_time 是 oop面向对象开发的,所以可以继承, 如果是面向过程编程,使用模块级 + 函数的方式来编程,先改变模块的某个全局变量或者函数逻辑,只能使用猴子补丁技术,而且模块天然还是个单例,不适合多次猴子补丁 面向对象就是有优势.
class UtcNbTime(NbTime):
default_time_zone = NbTime.TIMEZONE_UTC
# 使用的时候
UtcNbTime()
class ShanghaiNbTime(NbTime):
default_time_zone = NbTime.TIMEZONE_ASIA_SHANGHAI
default_formatter = NbTime.FORMATTER_DATETIME_NO_ZONE
# 使用的时候
ShanghaiNbTime()
class PopularNbTime(NbTime):
@property
def ago_1_days(self):
return self.shift(days=-1)
@property
def ago_7_days(self):
return self.shift(days=-7)
@property
def ago_30_days(self):
return self.shift(days=-30)
@property
def ago_180_days(self):
return self.shift(days=-180)
总结就是 NbTime 的入参接受所有类型,NbTime支持链式调用,Nbtime方便支持时区,Nbtime方便操作时间转化,
所以NbTime操作时间,远远暴击使用datetime和三方arrow包,
远远暴击用户在 utils.time_utils.py文件中写几百个孤立的面向过程操作时间的函数.