[Datetime-SIG] PEP-0500 (Alternative datetime arithmetic) Was: PEP 495 ... is ready ...

Alexander Belopolsky alexander.belopolsky at gmail.com
Wed Aug 19 01:42:00 CEST 2015


On Tue, Aug 18, 2015 at 7:12 PM, Guido van Rossum <guido at python.org> wrote:

>
>> [Guido van Rossum]
>>
>>> Similar for adding a datetime and a timedelta. Optimizing this should
>>> be  IMO the only question is how should a datetime object choose between
>>> classic arithmetic[1] and timeline arithmetic. My proposal here is to make
>>> that a boolean property of the tzinfo object -- we could either use a
>>> marker subclass or an attribute whose absence implies classic arithmetic.
>>>
>>
>> With this proposal, we will need something like this:
>>
>> def __sub__(self, other):
>>     if self.tzinfo is not None and self.tzinfo.strict:
>>         self_offset = self.utcoffset()
>>         other_offset = other.utcoffset()
>>         naive_self = self.replace(tzinfo=None)
>>         naive_other = other.replace(tzinfo=None)
>>         return naive_self - self_offset - naive_other + other_offset
>>     # old logic
>>
>> So we need to create six intermediate Python objects just to do the
>> math.  On top of that, we need the utcoffset() method which is a pain to
>> write in C, so we will wrap our optimized dst() function and compute
>> utcoffset() as dst(t) + timedelta(hours=-5), creating four more
>> intermediate Python objects.  At the end of the day, I will not be
>> surprised if aware datetime subtraction is 10x slower than naive and every
>> Python textbook recommends to avoid doing arithmetic with aware datetime
>> objects.
>>
>>
> I doubt it. Most textbooks aren't that concerned with saving a few cycles.
> (Do most Python textbooks even discuss the cost of object creation or
> function calls?) Anyways, wouldn't PEP 500 be even slower?
>

I don't think so.  We can implement PEP 500 as a C equivalent of

def __sub__(self, other):
    try:
        try:
           return self.tzinfo.__datetime_diff__(self, other)
        except TypeError: # assume other is a timedelta
           return self.tzinfo.__datetime_sub__(self, other)
    except AttributeError: # assume missing PDDM
        pass
    # old logic

and __datetime_diff__ / __datetime_sub__ may be even faster than a single
timedelta - timedelta operation because no timezone would support a time
span of more than a century or two and can do even microsecond-precision
calculations in machine integers.

Granted, most timezone implementations will just implement .utcoffset() and
inherit the slow __datetime_sub/diff__ implementations from tzstrict, but
users who care about a few simple timezones will have an option to optimize
those.
-------------- next part --------------
An HTML attachment was scrubbed...
URL: <http://mail.python.org/pipermail/datetime-sig/attachments/20150818/526acede/attachment.html>


More information about the Datetime-SIG mailing list