Various test, code and docs fixups

This commit is contained in:
Robert Schulze 2023-01-13 14:01:13 +00:00
parent 4ea836b87e
commit bd41c74ddf
No known key found for this signature in database
GPG Key ID: 26703B55FB13728A
6 changed files with 94 additions and 50 deletions

View File

@ -207,9 +207,11 @@ Converts a date or date with time to a UInt8 number containing the number of the
Aliases: `DAYOFMONTH`, `DAY`.
## toDayOfWeek(date\[,mode\])
## toDayOfWeek
Converts a date or date with time to a UInt8 number containing the number of the day of the week. The two-argument form of toDayOfWeek() enables you to specify whether the week starts on Monday or Sunday, and whether the return value should be in the range from 0 to 6 or from 1-7. If the mode argument is ommited, the default mode is 0.
Converts a date or date with time to a UInt8 number containing the number of the day of the week.
The two-argument form of `toDayOfWeek()` enables you to specify whether the week starts on Monday or Sunday, and whether the return value should be in the range from 0 to 6 or 1 to 7. If the mode argument is ommited, the default mode is 0. The time zone of the date can be specified as the third argument.
| Mode | First day of week | Range |
|------|-------------------|------------------------------------------------|
@ -220,6 +222,12 @@ Converts a date or date with time to a UInt8 number containing the number of the
Alias: `DAYOFWEEK`.
**Syntax**
``` sql
toDayOfWeek(t[, mode[, timezone]])
```
## toHour
Converts a date with time to a UInt8 number containing the number of the hour in 24-hour time (0-23).
@ -323,11 +331,17 @@ If `toLastDayOfMonth` is called with an argument of type `Date` greater then 214
Rounds down a date, or date with time, to the nearest Monday.
Returns the date.
## toStartOfWeek(t\[,mode\])
## toStartOfWeek
Rounds down a date, or date with time, to the nearest Sunday or Monday by mode.
Rounds a date or date with time down to the nearest Sunday or Monday.
Returns the date.
The mode argument works exactly like the mode argument to toWeek(). For the single-argument syntax, a mode value of 0 is used.
The mode argument works exactly like the mode argument in function `toWeek()`. If no mode is specified, mode is assumed as 0.
**Syntax**
``` sql
toStartOfWeek(t[, mode[, timezone]])
```
## toStartOfDay
@ -462,10 +476,12 @@ Converts a date, or date with time, to a UInt16 number containing the ISO Year n
Converts a date, or date with time, to a UInt8 number containing the ISO Week number.
## toWeek(date\[,mode\])
## toWeek
This function returns the week number for date or datetime. The two-argument form of `toWeek()` enables you to specify whether the week starts on Sunday or Monday and whether the return value should be in the range from 0 to 53 or from 1 to 53. If the mode argument is omitted, the default mode is 0.
`toISOWeek()` is a compatibility function that is equivalent to `toWeek(date,3)`.
This function returns the week number for date or datetime. The two-argument form of toWeek() enables you to specify whether the week starts on Sunday or Monday and whether the return value should be in the range from 0 to 53 or from 1 to 53. If the mode argument is omitted, the default mode is 0.
`toISOWeek()`is a compatibility function that is equivalent to `toWeek(date,3)`.
The following table describes how the mode argument works.
| Mode | First day of week | Range | Week 1 is the first week … |
@ -489,13 +505,15 @@ For mode values with a meaning of “with 4 or more days this year,” weeks are
For mode values with a meaning of “contains January 1”, the week contains January 1 is week 1. It does not matter how many days in the new year the week contained, even if it contained only one day.
**Syntax**
``` sql
toWeek(date, [, mode][, Timezone])
toWeek(t[, mode[, time_zone]])
```
**Arguments**
- `date` Date or DateTime.
- `t` Date or DateTime.
- `mode` Optional parameter, Range of values is \[0,9\], default is 0.
- `Timezone` Optional parameter, it behaves like any other conversion function.
@ -511,13 +529,19 @@ SELECT toDate('2016-12-27') AS date, toWeek(date) AS week0, toWeek(date,1) AS we
└────────────┴───────┴───────┴───────┘
```
## toYearWeek(date\[,mode\])
## toYearWeek
Returns year and week for a date. The year in the result may be different from the year in the date argument for the first and the last week of the year.
The mode argument works exactly like the mode argument to toWeek(). For the single-argument syntax, a mode value of 0 is used.
The mode argument works exactly like the mode argument to `toWeek()`. For the single-argument syntax, a mode value of 0 is used.
`toISOYear()`is a compatibility function that is equivalent to `intDiv(toYearWeek(date,3),100)`.
`toISOYear()` is a compatibility function that is equivalent to `intDiv(toYearWeek(date,3),100)`.
**Syntax**
``` sql
toYearWeek(t[, mode[, timezone]])
```
**Example**

View File

@ -636,14 +636,17 @@ public:
inline UInt8 toDayOfWeek(DateOrTime v, UInt8 week_day_mode) const
{
WeekDayMode mode = check_week_day_mode(week_day_mode);
UInt8 res = toDayOfWeek(v);
bool start_from_sunday = (mode == WeekDayMode::WeekStartsSunday0 || mode == WeekDayMode::WeekStartsSunday1);
bool zero_based = (mode == WeekDayMode::WeekStartsMonday0 || mode == WeekDayMode::WeekStartsSunday0);
UInt8 res = toDayOfWeek(v);
using enum WeekDayMode;
bool start_from_sunday = (mode == WeekStartsSunday0 || mode == WeekStartsSunday1);
bool zero_based = (mode == WeekStartsMonday0 || mode == WeekStartsSunday0);
if (start_from_sunday)
res = res % 7 + 1;
if (zero_based)
--res;
return res;
}
@ -875,7 +878,6 @@ public:
return static_cast<WeekDayMode>(mode & 3);
}
/** Calculate weekday from d.
* Returns 0 for monday, 1 for tuesday...
*/

View File

@ -786,21 +786,21 @@ struct ToDayOfWeekImpl
{
static constexpr auto name = "toDayOfWeek";
static inline UInt8 execute(Int64 t, UInt8 week_day_mode, const DateLUTImpl & time_zone)
static inline UInt8 execute(Int64 t, UInt8 mode, const DateLUTImpl & time_zone)
{
return time_zone.toDayOfWeek(t, week_day_mode);
return time_zone.toDayOfWeek(t, mode);
}
static inline UInt8 execute(UInt32 t, UInt8 week_day_mode, const DateLUTImpl & time_zone)
static inline UInt8 execute(UInt32 t, UInt8 mode, const DateLUTImpl & time_zone)
{
return time_zone.toDayOfWeek(t, week_day_mode);
return time_zone.toDayOfWeek(t, mode);
}
static inline UInt8 execute(Int32 d, UInt8 week_day_mode, const DateLUTImpl & time_zone)
static inline UInt8 execute(Int32 d, UInt8 mode, const DateLUTImpl & time_zone)
{
return time_zone.toDayOfWeek(ExtendedDayNum(d), week_day_mode);
return time_zone.toDayOfWeek(ExtendedDayNum(d), mode);
}
static inline UInt8 execute(UInt16 d, UInt8 week_day_mode, const DateLUTImpl & time_zone)
static inline UInt8 execute(UInt16 d, UInt8 mode, const DateLUTImpl & time_zone)
{
return time_zone.toDayOfWeek(DayNum(d), week_day_mode);
return time_zone.toDayOfWeek(DayNum(d), mode);
}
using FactorTransform = ToMondayImpl;

View File

@ -82,8 +82,8 @@ protected:
arguments[0].type->getName(), getName());
if (!isUInt8(arguments[1].type))
throw Exception(ErrorCodes::ILLEGAL_TYPE_OF_ARGUMENT,
"Illegal type of 2nd (optional) argument of function {}. Must be constant UInt8 (week mode).",
getName());
"Illegal type {} of 2nd (optional) argument of function {}. Must be constant UInt8 (week mode).",
arguments[1].type->getName(), getName());
}
else if (arguments.size() == 3)
{
@ -93,12 +93,12 @@ protected:
arguments[0].type->getName(), getName());
if (!isUInt8(arguments[1].type))
throw Exception(ErrorCodes::ILLEGAL_TYPE_OF_ARGUMENT,
"Illegal type of 2nd (optional) argument of function {}. Must be constant UInt8 (week mode).",
getName());
"Illegal type {} of 2nd (optional) argument of function {}. Must be constant UInt8 (week mode).",
arguments[1].type->getName(), getName());
if (!isString(arguments[2].type))
throw Exception(ErrorCodes::ILLEGAL_TYPE_OF_ARGUMENT,
"Illegal type of 3rd (optional) argument of function {}. Must be constant string (timezone name).",
getName());
"Illegal type {} of 3rd (optional) argument of function {}. Must be constant string (timezone name).",
arguments[2].type->getName(), getName());
if ((isDate(arguments[0].type) || isDate32(arguments[0].type)) && is_result_type_date_or_date32)
throw Exception(ErrorCodes::ILLEGAL_TYPE_OF_ARGUMENT,
"The timezone argument of function {} is allowed only when the 1st argument is DateTime or DateTime64.",

View File

@ -6,7 +6,6 @@
<value>toSecond</value>
<value>toMinute</value>
<value>toHour</value>
<value>toDayOfWeek</value>
<value>toDayOfMonth</value>
<value>toDayOfYear</value>
<value>toMonth</value>
@ -47,21 +46,33 @@
<value>toUnixTimestamp</value>
</values>
</substitution>
<substitution>
<name>datetime_transform_with_mode</name>
<values>
<value>toDayOfWeek</value>
<value>toStartOfWeek</value>
<value>toWeek</value>
<value>toYearWeek</value>
</values>
</substitution>
<substitution>
<name>date_transform</name>
<values>
<value>toDayOfWeek</value>
<value>toDayOfMonth</value>
<value>toDayOfWeek</value>
<value>toDayOfYear</value>
<value>toWeek</value>
<value>toMonth</value>
<value>toQuarter</value>
<value>toYear</value>
<value>toYearWeek</value>
<value>toISOWeek</value>
<value>toISOYear</value>
<value>toDate</value>
<value>toMonday</value>
<value>toStartOfDay</value>
<value>toStartOfWeek</value>
<value>toStartOfMonth</value>
<value>toStartOfQuarter</value>
<value>toStartOfYear</value>
@ -79,14 +90,6 @@
<value>toRelativeQuarterNum</value>
</values>
</substitution>
<substitution>
<name>time_zone</name>
<values>
<value>UTC</value>
<value>Asia/Istanbul</value>
<value>Asia/Kolkata</value>
</values>
</substitution>
<substitution>
<name>binary_function</name>
<values>
@ -116,11 +119,21 @@
<value>subtractYears</value>
</values>
</substitution>
<substitution>
<name>time_zone</name>
<values>
<value>UTC</value>
<value>Asia/Istanbul</value>
<value>Asia/Kolkata</value>
</values>
</substitution>
</substitutions>
<query>SELECT count() FROM numbers(50000000) WHERE NOT ignore(toDateTime('2017-01-01 00:00:00') + number % 100000000 + rand() % 100000 AS t, {datetime_transform}(t, '{time_zone}'))</query>
<query>SELECT count() FROM numbers(50000000) WHERE NOT ignore(toDateTime('2017-01-01 00:00:00') + number % 100000000 + rand() % 100000 AS t, {datetime_transform_with_mode}(t, 0, '{time_zone}'))</query>
<query>SELECT count() FROM numbers(50000000) WHERE NOT ignore(toDate('2017-01-01') + number % 1000 + rand() % 10 AS t, {date_transform}(t))</query>
<query>SELECT count() FROM numbers(50000000) WHERE NOT ignore(toDateTime('2017-01-01 00:00:00') + number % 100000000 + rand() % 100000 AS t, {binary_function}(t, 1))</query>
<query>SELECT count() FROM numbers(50000000) WHERE NOT ignore(toDateTime('2017-01-01 00:00:00') + number % 100000000 + rand() % 100000 AS t, toStartOfInterval(t, INTERVAL 1 month))</query>
<query>SELECT count() FROM numbers(50000000) WHERE NOT ignore(toDateTime('2017-01-01 00:00:00') + number % 100000000 + rand() % 100000 AS t, date_trunc('month', t))</query>
</test>

View File

@ -1,15 +1,12 @@
<!--
This is a performance smoke test for DateTime and Date. Some other basic functions are tested by date_time_64.xml, and a more
exhaustive list of functions is in date_time_long.xml (it's about an hour so we can't afford to test it on each commit).
-->
<test>
<!--
This is a short screening test for DateTime and Date. Some
other basic functions are tested by date_time_64, and a more
exhaustive list of functions is in date_time_long.xml (it's
about an hour so we can't afford to test it on each commit).
-->
<substitutions>
<substitution>
<name>date_transform</name>
<values>
<value>toDayOfWeek</value>
<value>toMonday</value>
<value>toRelativeDayNum</value>
<value>toYYYYMMDDhhmmss</value>
@ -32,16 +29,24 @@
</substitution>
</substitutions>
<!-- date_transform -->
<!-- {date_transform} -->
<query>SELECT count() FROM numbers(50000000) WHERE NOT ignore(toDateTime('2017-01-01 00:00:00') + number % 100000000 + rand() % 100000 AS t, {date_transform}(t, '{time_zone}'))</query>
<query>SELECT count() FROM numbers(50000000) WHERE NOT ignore(toDate('2017-01-01') + number % 1000 + rand() % 10 AS t, {date_transform}(t))</query>
<!-- toUnixTimestamp() -->
<query>SELECT count() FROM numbers(50000000) WHERE NOT ignore(toDateTime('2017-01-01 00:00:00') + number % 100000000 + rand() % 100000 AS t, toUnixTimestamp(t, '{time_zone}'))</query>
<!-- toUnixTimestamp(Date()) is pro5bit, wrap Date() with toUInt16() to overcome -->
<!-- toUnixTimestamp(Date()) is prohibited, wrap Date() with toUInt16() to overcome -->
<query>SELECT count() FROM numbers(50000000) WHERE NOT ignore(toDate('2017-01-01') + number % 1000 + rand() % 10 AS t, toUnixTimestamp(toUInt16(t)))</query>
<!-- {binary_function} -->
<query>SELECT count() FROM numbers(50000000) WHERE NOT ignore(toDateTime('2017-01-01 00:00:00') + number % 100000000 + rand() % 100000 AS t, {binary_function}(t, 1))</query>
<!-- misc -->
<query>SELECT count() FROM numbers(50000000) WHERE NOT ignore(toDateTime('2017-01-01 00:00:00') + number % 100000000 + rand() % 100000 AS t, toStartOfInterval(t, INTERVAL 1 month))</query>
<query>SELECT count() FROM numbers(50000000) WHERE NOT ignore(toDateTime('2017-01-01 00:00:00') + number % 100000000 + rand() % 100000 AS t, date_trunc('month', t))</query>
<query>SELECT count() FROM numbers(50000000) WHERE NOT ignore(toDateTime('2017-01-01 00:00:00') + number % 100000000 + rand() % 100000 AS t, toDayOfWeek(t, 0, '{time_zone}'))</query>
<query>SELECT count() FROM numbers(50000000) WHERE NOT ignore(toDate('2017-01-01') + number % 1000 + rand() % 10 AS t, toDayOfWeek(t))</query>
</test>