[local-time-devel] Proposed function: TIMESTAMP-ADD-DURATION
J.P. Larocque
jpl at thoughtcrime.us
Tue May 4 22:15:20 UTC 2010
Hi,
I have a need to add a duration (as a number of seconds) to a
TIMESTAMP--a function that is complementary to TIMESTAMP-DIFFERENCE.
TIMESTAMP+ with a unit of :SEC doesn't work for me, because:
1) I want the ability to pass a non-integer number of seconds, such
as 3.25d0 or 1/4, and get a new timestamp with DAY, SEC, and NSEC
updated accordingly. Currently I'd have to call TIMESTAMP+ twice
and do a lot of busywork that LOCAL-TIME should be able to do for
me. (Or call TIMESTAMP+ with an NSEC of (floor (* seconds (expt
10 9))), but that's also quite ugly.)
2) TIMESTAMP+ depends on %OFFSET-TIMESTAMP-PART, which has at least
one DST bug. When you give either function a unit of :DAY,
:MONTH, :YEAR, etc., it will treat its given timestamp as a
calendar date and time of day and perform the manipulation on the
calendar date and time of day, converting the result back to an
absolute time. For example, adding 1 day to
2010-03-13T10:00-08:00 in Pacific Standard Time results in
2010-03-14T10:00-07:00 Pacific Daylight Time). That's fine, as
that seems to be intended. However, nanoseconds spill over into
seconds, and seconds spill over into days, so even if I want
exactly 86400 seconds, TIMESTAMP+ treats my request as if I had
asked for 1 calendar day:
CL-USER> local-time:*default-timezone* ; = America/Los_Angeles
#<LOCAL-TIME::TIMEZONE PDT PST PWT PPT>
CL-USER> (let* ((ts1 (local-time:encode-timestamp
0 0 0 10 13 3 2010))
(ts2 (local-time:timestamp+ ts1 86400 :sec)))
(values ts1 ts2
(local-time:timestamp-difference ts2 ts1)))
@2010-03-13T10:00:00.000000-08:00
@2010-03-14T10:00:00.000000-07:00
82800
Because of the inconvenience of #1, and the bug of #2 caused by
confusing calendar dates/times of day with abstract, absolute points
in time, I propose a new function, TIMESTAMP-ADD-DURATION. It's as
simple as can be: add a number of seconds to a timestamp; no
consideration of time zones or DST is necessary at all. I've attached
a patch that includes documentation.
Hope you find it useful,
--
J.P. Larocque <jpl at thoughtcrime.us>
-------------- next part --------------
Tue May 4 15:13:27 PDT 2010 J.P. Larocque <jpl at thoughtcrime.us>
* Add function TIMESTAMP-ADD-DURATION.
New patches:
[Add function TIMESTAMP-ADD-DURATION.
J.P. Larocque <jpl at thoughtcrime.us>**20100504221327] {
hunk ./doc/local-time.texinfo 448
+
+ at itindex timestamp-add-duration
+ at defun timestamp-add-duration time duration
+
+Adds @var{duration} to @var{time}, returning a new @code{timestamp}
+with the resulting time. @var{duration} is a @code{real} number of
+seconds occurring after @var{time}.
+
+ at var{duration} may be positive or negative, indicating a time later
+than or prior to @var{time}. @var{duration} may be an integer, in
+which case the returned @code{timestamp} will have the same
+ at code{nsec} value as @var{time}, or it may have a subsecond fractional
+part, in which case @code{nsec} is updated as expected.
+ at end defun
+
+
hunk ./src/local-time.lisp 58
+ #:timestamp-add-duration
hunk ./src/local-time.lisp 954
+(defun timestamp-add-duration (time duration)
+ "Adds DURATION to TIME, returning a new TIMESTAMP with the resulting time. DURATION is a REAL number of seconds occurring after TIME."
+ (declare (type timestamp time)
+ (type real duration))
+ (let ((sec (+ (* (day-of time) +seconds-per-day+)
+ (sec-of time)
+ (/ (nsec-of time) #.(expt 10 9))
+ (rational duration))))
+ (multiple-value-bind (sec subsec) (floor sec)
+ (multiple-value-bind (day sec) (floor sec +seconds-per-day+)
+ (make-timestamp :day day :sec sec
+ :nsec (floor subsec #.(expt 10 -9)))))))
+
}
Context:
[TODO file
attila.lendvai at gmail.com**20100420063102
Ignore-this: c6136055d112035c5df541adde00d862
]
[no need to :shadow #:time anymore because it's called time-of-day now
attila.lendvai at gmail.com**20100419193011
Ignore-this: b7dbc95244891992951f58265ab368aa
]
[Updated copyright year for probably no reason
Daniel Lowe <dlowe at bitmuse.com>**20100324195045
Ignore-this: 76fb8af82a60d2f4c0e952febde10363
]
[Many default offset inconsistencies resolved, more tests pass
Daniel Lowe <dlowe at bitmuse.com>**20100324194517
Ignore-this: b414446d02273d5e75b9a93bed5ca6fa
]
[Fixed offset bug in minimize and maximize part functions
Daniel Lowe <dlowe at bitmuse.com>**20100324152342
Ignore-this: b58b5e69598805c9b30a6b600560ade
]
[fix parentheses from last patch
jaap at streamtech.nl**20100209114731
Ignore-this: a70910106b446020eed799cebab65b6c
]
[roll back my change where adjust-timestamp defaulted to UTC (both are broken, but this way it's at least backwards compatible)
attila.lendvai at gmail.com**20100209102239
Ignore-this: 63f876b8f1bf5483e874b3dbc0d4e177
]
[use hu.dwim.stefil for unit testing.
attila.lendvai at gmail.com**20100127081740
Ignore-this: e5ddf9db232c9723b233e19ba1c9948c
useful things for copy/pasting:
darcs get http://common-lisp.net/project/alexandria/darcs/alexandria/
darcs get http://dwim.hu/darcs/hu.dwim.stefil
(asdf:test-system :local-time)
]
[follow documentation/ -> doc/ rename in .boring
attila.lendvai at gmail.com**20100127081710
Ignore-this: 2ea403b64f5ada4b2e9dbb4b013b99b9
]
[added a (check-type result time-of-day) in cl-postgres integration
attila.lendvai at gmail.com**20100126123531
Ignore-this: 4750c6ffaa3e8ed41d10fe2fb9d5b229
]
[renamed 'time to 'time-of-day for less conflict headaches
attila.lendvai at gmail.com**20100126123505
Ignore-this: 50b518114f386d042701ad92260e4794
]
[fix valid-date-p
attila.lendvai at gmail.com**20091206211948
Ignore-this: 207df3b76010adf3a2e749fe9d60db57
]
[Added date and time types.
levente.meszaros at gmail.com**20091201201849
Ignore-this: b858bbe9a6b10f4ed106fba83d69e406
]
[Split local-time.asd and introduce cl-postgres+local-time.asd.
levente.meszaros at gmail.com**20091009161856
Ignore-this: 3e4521adc1a0afa273c63d304cd6e9c8
]
[TAG before controversial changes
Daniel Lowe <dlowe at bitmuse.com>**20100126123450
Ignore-this: 7f2ec6e3a5baa0691637367f1b22aed
]
[fix test adjust-timestamp/bug3 (PLEASE AUDIT!)
attila.lendvai at gmail.com**20100125122540
Ignore-this: 6b449034e6c96f245709a808c5e14593
]
[fix test adjust-timestamp/bug2 (PLEASE AUDIT!)
attila.lendvai at gmail.com**20100125122530
Ignore-this: 212178187413618cb83e4e7d0bd8658e
]
[adjust-timestamp defaults to :utc-offset 0 unless timezone is specified. fixes surprises shown by test adjust-timestamp/bug2 (PLEASE AUDIT!)
attila.lendvai at gmail.com**20100125122507
Ignore-this: 1eff627c0e5d072b89d7119c4426f229
]
[added adjust-timestamp/bug3
attila.lendvai at gmail.com**20100125121843
Ignore-this: 2c3cd77b1f107152dd36633734ae4ae
]
[whitespace
attila.lendvai at gmail.com**20100125120759
Ignore-this: 341ea584efa430672b4a7fae8368184a
]
[added test adjust-timestamp/bug2
attila.lendvai at gmail.com**20100124185450
Ignore-this: 996991645615afe1a9a6be8cef3c7a4f
]
[Fix SBCL conditional compilation
Jonathan Lee <jonathlee at gmail.com>**20100102181805
Ignore-this: e084a602df8e1931fff11d4d9f6ba814
]
[Updated asdf version number to 1.0.1
dlowe at bitmuse.com**20100111031331
Ignore-this: 17e00a012590c5116fbdeb86566b1786
]
[added +months-per-year+
attila.lendvai at gmail.com**20091202102038
Ignore-this: 5c1c99bee45537409939c4da0ada1075
]
[another take on reread-timezone-repository & co.
attila.lendvai at gmail.com**20091030235517
Ignore-this: ad00124eea993a623c42e0cd9b6ad81c
]
[try to make the initialization of *project-home-directory* a bit less fragile when not loading through ASDF
attila.lendvai at gmail.com**20091030093403
Ignore-this: 5a848c282db52a5edb38df6fdf9c186e
although i personally am much more interested in making local-time load with xcvb, than keeping it in one
file that can be CL:LOAD'ed...
]
[make it loadable with (load "local-time.lisp")
attila.lendvai at gmail.com**20091030092409
Ignore-this: b3aae958e1003af861646fda0f036c9d
]
[fix #+#. voodoo, one less compilation warning
attila.lendvai at gmail.com**20091030091812
Ignore-this: b80cc242457896e43c168c9fdc1aadf3
]
[formatting, semantically NOP
attila.lendvai at gmail.com**20091030091743
Ignore-this: 6edfb0b406108f1b3cd296a245dac55f
]
[whitespace changes, one less warning
attila.lendvai at gmail.com**20091029122310
Ignore-this: 6a319ea0491a85a8bd270a2468c7b47a
]
[added a deftype for timezone-offset, fix bug reported by Abhishek Reddy and Huw Giddens
attila.lendvai at gmail.com**20091029122004
Ignore-this: a3e828c02dcdf1d195311cfe5305ec6f
http://common-lisp.net/pipermail/local-time-devel/2009-October/000173.html
]
[some tests
attila.lendvai at gmail.com**20091029121803
Ignore-this: 9c510d5a16519beeeed2738d290742a1
]
[Don't discard value of sb-ext:get-time-of-day
Daniel Lowe <dlowe at bitmuse.com>**20091022155025
Ignore-this: 565ad4c1ee49c11d900c3e1781e9f6e0
]
[Provide support for formatting the day as an ordinal (e.g. 1st, 22nd)
Daniel White <daniel at whitehouse.id.au>**20091022132601
Ignore-this: c166703967661a3d7e32a4489184fdd4
]
[fix test: reread-timezone-repository is not public in local-time package (anymore?)
attila.lendvai at gmail.com**20091005090107
Ignore-this: 8e3f2381c3c11afdd5123055e332f904
]
[comments
attila.lendvai at gmail.com**20091002083019
Ignore-this: 855a9b7004e33350c0a0394e242f459d
]
[ccl-windows-without-gettimeofday
essdir at web.de**20090901164212
Ignore-this: b6df4f6bd69eff0d6fd18dc1a90097e7
]
[Minor bugfix: :utc-offset instead of :offset
Maciej Katafiasz <mathrick at gmail.com>**20090808135148
Ignore-this: e20b7cff5ec220a83bd112265b06f99f
]
[follow the format-rfcnumber-timestring nameing convention, rename format-http-timestring
attila.lendvai at gmail.com**20090928091959
Ignore-this: a35c5d543cabb520ff676c9a490f1cb2
]
[Make timestamp manipulation functions take and respect timezone arguments.
Maciej Katafiasz <mathrick at gmail.com>**20090727180103
Ignore-this: 79214728e4966f44d8d4587bd850c53b
]
[Make WITH-DECODED-TIMESTAMP and related take timezone/offset arguments.
Maciej Katafiasz <mathrick at gmail.com>**20090727175400
Ignore-this: 296084f8d9179fe257c69118b7123309
]
[Make ENCODE-TIMESTAMP accept timezones instead of fixed offsets.
Maciej Katafiasz <mathrick at gmail.com>**20090727174013
Ignore-this: f6420e93d194396afb221821e1312652
]
[update TODO, add link to chronicity
attila.lendvai at gmail.com**20090729181326
Ignore-this: aa290ebfb4f6001600cf33a228a99a41
]
[Use symbols instead of strings where possible.
Maciej Katafiasz <mathrick at gmail.com>**20090724164920]
[added a once failing test
attila.lendvai at gmail.com**20090616143818
Ignore-this: 741ad01d47b47e15cb4877567d3ba9d9
]
[add a more useful error when find-timezone-by-location-name is used without reading in the timezone files
attila.lendvai at gmail.com**20090616143733
Ignore-this: c982ca27ef16e7f865afece963b6c9be
]
[fix (print (now)) when *timezone* is (find-timezone-by-location-name "UTC")
attila.lendvai at gmail.com**20090616141707
Ignore-this: ac694826aa5e9719d41c51503e0a8785
]
[clean up gettimeofday stuff, follow sbcl's changes (but remain backward compatible)
attila.lendvai at gmail.com**20090521170712
Ignore-this: 70b2754c0a254abb060dce0f15bb266
]
[remove superfluous eval-when around reread-timezone-repository
attila.lendvai at gmail.com**20090513213236
Ignore-this: 337cf4b3d50d0714f2c4a4a3d84e356f
]
[Local-time now passes all tests in CCL
Daniel Lowe <dlowe at bitmuse.com>**20090417142203]
[Changed lispworks/ccl kluge to another, better kluge
Daniel Lowe <dlowe at bitmuse.com>**20090417142156]
[In WITH-DECODED-TIMESTAMP, declare nsec type as ranged integer instead of FIXNUM
Daniel Lowe <dlowe at bitmuse.com>**20090416204555]
[clarification comment for the lispworks #_ situation
attila.lendvai at gmail.com**20090324135651
Ignore-this: 1f97d85c23ecffd5806f7a3c137f8491
]
[Less intrusive version of the Lispworks patch for #_.
Larry Clapp <larry at theclapp.org>**20090324132813
Use an around method in ASDF's compile-op to set the readtable to ignore #_.
This achieves the same end, but more elegantly, and doesn't pollute the
regular readtable.
]
[be more conservative when installing global reader macros as a lispwork workaround
attila.lendvai at gmail.com**20090323142133
Ignore-this: dca64a6f7daa4d478beba41d1c102a16
]
[Work with Lispworks
Larry Clapp <larry at theclapp.org>**20090323132602
- Added a dummy reader macro for #_ so the
#+ccl
(... #_gettimeofday ... )
doesn't break the compile
- Fix %unix-gettimeofday for Lisps other than CMU, SBCL, and CCL.
]
[TAG local-time-1.0.1
Daniel Lowe <dlowe at bitmuse.com>**20090312154109]
Patch bundle hash:
f755fcabbb233c18fe2987311facd95aec666ae6
More information about the local-time-devel
mailing list