python datetime delta inaccuracy - Sidereal period

141 Views Asked by At

In python datatime module I noticed a gap. Datetime does leap year adjustment automatically, using sidereal year length.

How to achieve scientific accuracy in these date calculations?

The difference is expected to be exactly 200, but it is 199.99377806650291

This is messing up the accuracy of the application.

Sidereal year days = 365.256363004

Expected difference is exactly 200 using 365.256363004. 2103-1903 = 200

>>> s = datetime.datetime(1903,1,1,0,0,0)
>>> s.strftime("%A, %d. %B %Y %I:%M%p")
'Thursday, 01. January 1903 12:00AM'
>>> 
>>> e = datetime.datetime(2103,1,1,0,0,0)
>>> e.strftime("%A, %d. %B %Y %I:%M%p")
'Monday, 01. January 2103 12:00AM'
>>> 
>>> e-s
datetime.timedelta(days=73049)
>>> s-e
datetime.timedelta(days=-73049)
>>> 

Error -

datetime calculated time delta 73049 days.

I think time delta should return 200 * 365.256363004 = 73051.2726008 days.

73049 / 365.256363004 = 199.99377806650291

200 - 199.99377806650291 = 0.0062219334971 #expected - calculated = error

365.256363004 * 24 * 60 = 525969.16272576 minutes #minutes in a Sidereal year

365.256363004 * 24 * 60 * 60 = 31558149.7635456 seconds #seconds in a Sidereal year

365.256363004 * 0.0062219334971 = 2.272600800003505 days #error in days

525969.16272576 * 0.0062219334971 = 3272.545152005046885 minutes #error in minutes

31558149.7635456 * 0.0062219334971 = 196352.709120302813103 seconds #error in seconds

It seems datetime is using 365.25 instead of all significant digits 365.256363004. 0.256363004 * 4 = 1.025452016 - 1 = 0.025452016 is ignored over leap year adjustments, not tracked by datetime that is causing error in scientific calculations.

1

There are 1 best solutions below

8
Mark Ransom On

The number of days being returned is exactly correct:

>>> def is_leap(y):
    return (y % 4 == 0) and ((y % 100 != 0) or (y % 400 == 0))

>>> sum(366 if is_leap(y) else 365 for y in range(1903,2103))
73049

The problem is your expectation that a year is exactly 365.256363004 days. It is trivially easy to prove that this is not the case. Calculate the difference between any two consecutive years, and the difference will be either 365 days or 366 days. It will never be a non-integer.