Python: datetime.tzinfo

 

datetime.datetime & datetime.time 两个类构造时可传tzinfo参数, 都会把tzinfo绑定到self._tzinfo属性上, 可通过tzinfo属性访问

 

 

 

 

__str__依次调用一下方法

 

 

 

 

 

 

 

 

 

class tzinfo:
    """Abstract base class for time zone info classes.

    Subclasses must override the name(), utcoffset() and dst() methods.
    """
    __slots__ = ()

    def tzname(self, dt):
        "datetime -> string name of time zone."
        raise NotImplementedError("tzinfo subclass must override tzname()")

    def utcoffset(self, dt):
        "datetime -> timedelta, positive for east of UTC, negative for west of UTC"
        raise NotImplementedError("tzinfo subclass must override utcoffset()")

    def dst(self, dt):
        """datetime -> DST offset as timedelta, positive for east of UTC.

        Return 0 if DST not in effect.  utcoffset() must include the DST
        offset.
        """
        raise NotImplementedError("tzinfo subclass must override dst()")

    def fromutc(self, dt):
        "datetime in UTC -> datetime in local time."

        if not isinstance(dt, datetime):
            raise TypeError("fromutc() requires a datetime argument")
        if dt.tzinfo is not self:
            raise ValueError("dt.tzinfo is not self")

        dtoff = dt.utcoffset()
        if dtoff is None:
            raise ValueError("fromutc() requires a non-None utcoffset() "
                             "result")

        # See the long comment block at the end of this file for an
        # explanation of this algorithm.
        dtdst = dt.dst()
        if dtdst is None:
            raise ValueError("fromutc() requires a non-None dst() result")
        delta = dtoff - dtdst
        if delta:
            dt += delta
            dtdst = dt.dst()
            if dtdst is None:
                raise ValueError("fromutc(): dt.dst gave inconsistent "
                                 "results; cannot convert")
        return dt + dtdst

    # Pickle support.

    def __reduce__(self):
        getinitargs = getattr(self, "__getinitargs__", None)
        if getinitargs:
            args = getinitargs()
        else:
            args = ()
        getstate = getattr(self, "__getstate__", None)
        if getstate:
            state = getstate()
        else:
            state = getattr(self, "__dict__", None) or None
        if state is None:
            return (self.__class__, args)
        else:
            return (self.__class__, args, state)

 

datetime.tzinfo 抽象类 Abstract class

三个抽象方法: tzname, utcoffset, dst 子类必须override, 否则报 NotImplementedError

 

  

其子类也不是实例化的,其是为了构造datetime.datetime & datetime.time 准备的

   

 调用datetime.datetime的tzname方法时,会调用实例的self._tzinfo的tzname方法,self._tzinfo是构造datetime.datetime实例时传递的tzinfo子类对象

因此dt就变成了datetime.datetime OR datetime.time 实例,这就是tzinfo类中的dt由来

 

import datetime
class UTC(datetime.tzinfo):
    def __init__(self,offset=0):
        self.__offset=offset

    def utcoffset(self,dt):
        return datetime.timedelta(hours=self.__offset)

    def tzname(self,dt):
        return 'UTC+%s dt: %s' % (self.__offset,[dt,id(dt)])

    def dst(self,dt):
        return datetime.timedelta(hours=self.__offset)


bj = datetime.datetime(2011, 11, 11, 0, 0, 0, tzinfo = UTC(8))
print(bj, id(bj))
print(bj.tzname())
print(bj.tzinfo)

 

 

bj.tzname()最终会调用UTC(8)实例的tzname方法

 

import datetime
class UTC(datetime.tzinfo):
    def __init__(self,offset=0):
        self.__offset=offset

    def utcoffset(self,dt):
        return datetime.timedelta(hours=self.__offset)

    def tzname(self,dt):
        return 'UTC+%s dt: %s' % (self.__offset,[dt,id(dt)])

    def dst(self,dt):
        return datetime.timedelta(hours=self.__offset)

#bj time
bj = datetime.datetime(2011, 11, 11, 0, 0, 0, tzinfo = UTC(8))
print("beijing time:",bj, id(bj))
print(bj.tzinfo)

#bangkok time
bangkok = datetime.datetime(2011,11,11,0,0,0,tzinfo = UTC(7))
print("bangkok time",bangkok)

#bj -> bangkok
print("beijing-time to bangkok-time:",bj.astimezone(UTC(7)),type(bj.astimezone(UTC(7))))

timespan=bj-bangkok
print("时差:",timespan,type(timespan))

 

 

bj & bangkok 时间由于tzinfo 的不同,产生了时差,相减生成datetime.timedelta对象

使用astimezone方法时,需要跟构造实例相同tzinfo子类对象,结果会转变时区

 

posted @ 2020-11-05 16:45  ascertain  阅读(709)  评论(0编辑  收藏  举报