mirror of
https://github.com/hanzoai/datastore.git
synced 2026-09-26 13:55:07 +00:00
addDays/subtractDays/addWeeks/subtractWeeks on DateTime/DateTime64 went through the per-row DateLUT calendar step even in UTC and other fixed-offset time zones, where a day/week is a constant 86400/604800 seconds. addSeconds/addMinutes/addHours already add n*k to the unix timestamp directly and are several times faster on the same data. Add an offset_is_fixed flag to DateLUTImpl, computed while filling the LUT: it is true iff the UTC offset never changes within the LUT range (no midnight jumps between consecutive days and no intra-day offset changes). When the flag is set, AddDaysImpl/AddWeeksImpl (and therefore subtractDays/subtractWeeks and the DateTime +/- INTERVAL DAY/WEEK operators) add delta * 86400 or delta * 604800 to the timestamp directly, skipping the LUT lookup and, for DateTime64/Time64, the std::div decomposition. Time zones with DST or any historical offset change keep the calendar path, as do MONTH/QUARTER/YEAR intervals. A parameterized unit test asserts for every known time zone that reports a fixed offset that DateLUTImpl::addDays is bitwise-equal to plain arithmetic across the LUT range. Co-Authored-By: Claude Fable 5 <[email protected]>
22 lines
872 B
XML
22 lines
872 B
XML
<test>
|
|
<settings>
|
|
<max_threads>1</max_threads>
|
|
</settings>
|
|
|
|
<substitutions>
|
|
<substitution>
|
|
<name>func</name>
|
|
<values>
|
|
<value>addDays</value>
|
|
<value>addWeeks</value>
|
|
<value>subtractDays</value>
|
|
<value>subtractWeeks</value>
|
|
</values>
|
|
</substitution>
|
|
</substitutions>
|
|
|
|
<query>SELECT sum(toUInt32({func}(t, 7))) FROM (SELECT toDateTime(1600000000 + number % 50000000, 'UTC') AS t FROM numbers(100000000))</query>
|
|
<query>SELECT sum(toUInt32({func}(t, 7))) FROM (SELECT toDateTime64(1600000000.123 + number % 50000000, 3, 'UTC') AS t FROM numbers(50000000))</query>
|
|
<query>SELECT sum(toUInt32({func}(t, 7))) FROM (SELECT toDateTime(1600000000 + number % 50000000, 'Europe/Berlin') AS t FROM numbers(50000000))</query>
|
|
</test>
|