Implement the 'sys_time' portions of the C++20 calendaring stuff. Reviewed as D56494

llvm-svn: 350929
This commit is contained in:
Marshall Clow 2019-01-11 15:12:04 +00:00
parent 40cd4b77e9
commit 5c08881343
21 changed files with 1210 additions and 143 deletions

View File

@ -1592,6 +1592,19 @@ using file_clock = _VSTD_FS::_FilesystemClock;
template<class _Duration>
using file_time = time_point<file_clock, _Duration>;
template <class _Duration>
using sys_time = time_point<system_clock, _Duration>;
using sys_seconds = sys_time<seconds>;
using sys_days = sys_time<days>;
struct local_t {};
template<class Duration>
using local_time = time_point<local_t, Duration>;
using local_seconds = local_time<seconds>;
using local_days = local_time<days>;
struct _LIBCPP_TYPE_VIS last_spec { explicit last_spec() = default; };
class _LIBCPP_TYPE_VIS day {
@ -1812,21 +1825,36 @@ private:
unsigned char __wd;
public:
weekday() = default;
explicit inline constexpr weekday(unsigned __val) noexcept: __wd(static_cast<unsigned char>(__val)) {}
// inline constexpr weekday(const sys_days& dp) noexcept;
// explicit constexpr weekday(const local_days& dp) noexcept;
inline explicit constexpr weekday(unsigned __val) noexcept : __wd(static_cast<unsigned char>(__val)) {}
inline constexpr weekday(const sys_days& __sysd) noexcept
: __wd(__weekday_from_days(__sysd.time_since_epoch().count())) {}
inline explicit constexpr weekday(const local_days& __locd) noexcept
: __wd(__weekday_from_days(__locd.time_since_epoch().count())) {}
inline constexpr weekday& operator++() noexcept { __wd = (__wd == 6 ? 0 : __wd + 1); return *this; }
inline constexpr weekday operator++(int) noexcept { weekday __tmp = *this; ++(*this); return __tmp; }
inline constexpr weekday& operator--() noexcept { __wd = (__wd == 0 ? 6 : __wd - 1); return *this; }
inline constexpr weekday operator--(int) noexcept { weekday __tmp = *this; --(*this); return __tmp; }
constexpr weekday& operator+=(const days& __dd) noexcept;
constexpr weekday& operator-=(const days& __dd) noexcept;
explicit inline constexpr operator unsigned() const noexcept { return __wd; }
inline explicit constexpr operator unsigned() const noexcept { return __wd; }
inline constexpr bool ok() const noexcept { return __wd <= 6; }
constexpr weekday_indexed operator[](unsigned __index) const noexcept;
constexpr weekday_last operator[](last_spec) const noexcept;
constexpr weekday_indexed operator[](unsigned __index) const noexcept;
constexpr weekday_last operator[](last_spec) const noexcept;
static constexpr unsigned char __weekday_from_days(int __days) noexcept;
};
// https://howardhinnant.github.io/date_algorithms.html#weekday_from_days
inline constexpr
unsigned char weekday::__weekday_from_days(int __days) noexcept
{
return static_cast<unsigned char>(
static_cast<unsigned>(__days >= -4 ? (__days+4) % 7 : (__days+5) % 7 + 6)
);
}
inline constexpr
bool operator==(const weekday& __lhs, const weekday& __rhs) noexcept
{ return static_cast<unsigned>(__lhs) == static_cast<unsigned>(__rhs); }
@ -2221,6 +2249,7 @@ constexpr year_month operator-(const year_month& __lhs, const months& __rhs) noe
constexpr year_month operator-(const year_month& __lhs, const years& __rhs) noexcept
{ return __lhs + -__rhs; }
class year_month_day_last;
class _LIBCPP_TYPE_VIS year_month_day {
private:
@ -2232,24 +2261,66 @@ public:
inline constexpr year_month_day(
const chrono::year& __yval, const chrono::month& __mval, const chrono::day& __dval) noexcept
: __y{__yval}, __m{__mval}, __d{__dval} {}
// inline constexpr year_month_day(const year_month_day_last& __ymdl) noexcept;
// inline constexpr year_month_day(const sys_days& dp) noexcept;
// inline explicit constexpr year_month_day(const local_days& dp) noexcept;
constexpr year_month_day(const year_month_day_last& __ymdl) noexcept;
inline constexpr year_month_day(const sys_days& __sysd) noexcept
: year_month_day(__from_days(__sysd.time_since_epoch())) {}
inline explicit constexpr year_month_day(const local_days& __locd) noexcept
: year_month_day(__from_days(__locd.time_since_epoch())) {}
constexpr year_month_day& operator+=(const months& __dm) noexcept;
constexpr year_month_day& operator-=(const months& __dm) noexcept;
constexpr year_month_day& operator+=(const years& __dy) noexcept;
constexpr year_month_day& operator-=(const years& __dy) noexcept;
inline constexpr chrono::year year() const noexcept { return __y; }
inline constexpr chrono::month month() const noexcept { return __m; }
inline constexpr chrono::day day() const noexcept { return __d; }
// inline constexpr operator sys_days() const noexcept;
// inline explicit constexpr operator local_days() const noexcept;
// TODO: This is not quite correct; requires the calendar bits to do right
// d_ is in the range [1d, (y_/m_/last).day()],
inline constexpr bool ok() const noexcept { return __y.ok() && __m.ok() && __d.ok(); }
inline constexpr chrono::year year() const noexcept { return __y; }
inline constexpr chrono::month month() const noexcept { return __m; }
inline constexpr chrono::day day() const noexcept { return __d; }
inline constexpr operator sys_days() const noexcept { return sys_days{__to_days()}; }
inline explicit constexpr operator local_days() const noexcept { return local_days{__to_days()}; }
constexpr bool ok() const noexcept;
static constexpr year_month_day __from_days(days __d) noexcept;
constexpr days __to_days() const noexcept;
};
// https://howardhinnant.github.io/date_algorithms.html#civil_from_days
inline constexpr
year_month_day
year_month_day::__from_days(days __d) noexcept
{
static_assert(std::numeric_limits<unsigned>::digits >= 18, "");
static_assert(std::numeric_limits<int>::digits >= 20 , "");
const int __z = __d.count() + 719468;
const int __era = (__z >= 0 ? __z : __z - 146096) / 146097;
const unsigned __doe = static_cast<unsigned>(__z - __era * 146097); // [0, 146096]
const unsigned __yoe = (__doe - __doe/1460 + __doe/36524 - __doe/146096) / 365; // [0, 399]
const int __yr = static_cast<int>(__yoe) + __era * 400;
const unsigned __doy = __doe - (365 * __yoe + __yoe/4 - __yoe/100); // [0, 365]
const unsigned __mp = (5 * __doy + 2)/153; // [0, 11]
const unsigned __dy = __doy - (153 * __mp + 2)/5 + 1; // [1, 31]
const unsigned __mth = __mp + (__mp < 10 ? 3 : -9); // [1, 12]
return year_month_day{chrono::year{__yr + (__mth <= 2)}, chrono::month{__mth}, chrono::day{__dy}};
}
// https://howardhinnant.github.io/date_algorithms.html#days_from_civil
inline constexpr days year_month_day::__to_days() const noexcept
{
static_assert(std::numeric_limits<unsigned>::digits >= 18, "");
static_assert(std::numeric_limits<int>::digits >= 20 , "");
const int __yr = static_cast<int>(__y) - (__m <= February);
const unsigned __mth = static_cast<unsigned>(__m);
const unsigned __dy = static_cast<unsigned>(__d);
const int __era = (__yr >= 0 ? __yr : __yr - 399) / 400;
const unsigned __yoe = static_cast<unsigned>(__yr - __era * 400); // [0, 399]
const unsigned __doy = (153 * (__mth + (__mth > 2 ? -3 : 9)) + 2) / 5 + __dy-1; // [0, 365]
const unsigned __doe = __yoe * 365 + __yoe/4 - __yoe/100 + __doy; // [0, 146096]
return days{__era * 146097 + static_cast<int>(__doe) - 719468};
}
inline constexpr
bool operator==(const year_month_day& __lhs, const year_month_day& __rhs) noexcept
{ return __lhs.year() == __rhs.year() && __lhs.month() == __rhs.month() && __lhs.day() == __rhs.day(); }
@ -2347,15 +2418,29 @@ public:
constexpr year_month_day_last& operator+=(const years& __y) noexcept;
constexpr year_month_day_last& operator-=(const years& __y) noexcept;
constexpr chrono::year year() const noexcept { return __y; }
constexpr chrono::month month() const noexcept { return __mdl.month(); }
constexpr chrono::month_day_last month_day_last() const noexcept { return __mdl; }
// constexpr chrono::day day() const noexcept;
// constexpr operator sys_days() const noexcept;
// explicit constexpr operator local_days() const noexcept;
constexpr bool ok() const noexcept { return __y.ok() && __mdl.ok(); }
inline constexpr chrono::year year() const noexcept { return __y; }
inline constexpr chrono::month month() const noexcept { return __mdl.month(); }
inline constexpr chrono::month_day_last month_day_last() const noexcept { return __mdl; }
constexpr chrono::day day() const noexcept;
inline constexpr operator sys_days() const noexcept { return sys_days{year()/month()/day()}; }
inline explicit constexpr operator local_days() const noexcept { return local_days{year()/month()/day()}; }
inline constexpr bool ok() const noexcept { return __y.ok() && __mdl.ok(); }
};
inline constexpr
chrono::day year_month_day_last::day() const noexcept
{
constexpr chrono::day __d[] =
{
chrono::day(31), chrono::day(28), chrono::day(31),
chrono::day(30), chrono::day(31), chrono::day(30),
chrono::day(31), chrono::day(31), chrono::day(30),
chrono::day(31), chrono::day(30), chrono::day(31)
};
return month() != February || !__y.is_leap() ?
__d[static_cast<unsigned>(month()) - 1] : chrono::day{29};
}
inline constexpr
bool operator==(const year_month_day_last& __lhs, const year_month_day_last& __rhs) noexcept
{ return __lhs.year() == __rhs.year() && __lhs.month_day_last() == __rhs.month_day_last(); }
@ -2429,6 +2514,15 @@ inline constexpr year_month_day_last& year_month_day_last::operator-=(const mont
inline constexpr year_month_day_last& year_month_day_last::operator+=(const years& __dy) noexcept { *this = *this + __dy; return *this; }
inline constexpr year_month_day_last& year_month_day_last::operator-=(const years& __dy) noexcept { *this = *this - __dy; return *this; }
inline constexpr year_month_day::year_month_day(const year_month_day_last& __ymdl) noexcept
: __y{__ymdl.year()}, __m{__ymdl.month()}, __d{__ymdl.day()} {}
inline constexpr bool year_month_day::ok() const noexcept
{
if (!__y.ok() || !__m.ok()) return false;
return chrono::day{1} <= __d && __d <= (__y / __m / last).day();
}
class _LIBCPP_TYPE_VIS year_month_weekday {
chrono::year __y;
chrono::month __m;
@ -2438,8 +2532,10 @@ public:
constexpr year_month_weekday(const chrono::year& __yval, const chrono::month& __mval,
const chrono::weekday_indexed& __wdival) noexcept
: __y{__yval}, __m{__mval}, __wdi{__wdival} {}
// constexpr year_month_weekday(const sys_days& dp) noexcept;
// explicit constexpr year_month_weekday(const local_days& dp) noexcept;
constexpr year_month_weekday(const sys_days& __sysd) noexcept
: year_month_weekday(__from_days(__sysd.time_since_epoch())) {}
inline explicit constexpr year_month_weekday(const local_days& __locd) noexcept
: year_month_weekday(__from_days(__locd.time_since_epoch())) {}
constexpr year_month_weekday& operator+=(const months& m) noexcept;
constexpr year_month_weekday& operator-=(const months& m) noexcept;
constexpr year_month_weekday& operator+=(const years& y) noexcept;
@ -2451,16 +2547,37 @@ public:
inline constexpr unsigned index() const noexcept { return __wdi.index(); }
inline constexpr chrono::weekday_indexed weekday_indexed() const noexcept { return __wdi; }
// constexpr operator sys_days() const noexcept;
// explicit constexpr operator local_days() const noexcept;
inline constexpr operator sys_days() const noexcept { return sys_days{__to_days()}; }
inline explicit constexpr operator local_days() const noexcept { return local_days{__to_days()}; }
inline constexpr bool ok() const noexcept
{
if (!__y.ok() || !__m.ok() || !__wdi.ok()) return false;
// TODO: make sure it's a valid date
return true;
}
static constexpr year_month_weekday __from_days(days __d) noexcept;
constexpr days __to_days() const noexcept;
};
inline constexpr
year_month_weekday year_month_weekday::__from_days(days __d) noexcept
{
const sys_days __sysd{__d};
const chrono::weekday __wd = chrono::weekday(__sysd);
const year_month_day __ymd = year_month_day(__sysd);
return year_month_weekday{__ymd.year(), __ymd.month(),
__wd[(static_cast<unsigned>(__ymd.day())-1)/7+1]};
}
inline constexpr
days year_month_weekday::__to_days() const noexcept
{
const sys_days __sysd = sys_days(__y/__m/1);
return (__sysd + (__wdi.weekday() - chrono::weekday(__sysd) + days{(__wdi.index()-1)*7}))
.time_since_epoch();
}
inline constexpr
bool operator==(const year_month_weekday& __lhs, const year_month_weekday& __rhs) noexcept
{ return __lhs.year() == __rhs.year() && __lhs.month() == __rhs.month() && __lhs.weekday_indexed() == __rhs.weekday_indexed(); }
@ -2538,11 +2655,22 @@ public:
inline constexpr chrono::month month() const noexcept { return __m; }
inline constexpr chrono::weekday weekday() const noexcept { return __wdl.weekday(); }
inline constexpr chrono::weekday_last weekday_last() const noexcept { return __wdl; }
// constexpr operator sys_days() const noexcept;
// explicit constexpr operator local_days() const noexcept;
inline constexpr operator sys_days() const noexcept { return sys_days{__to_days()}; }
inline explicit constexpr operator local_days() const noexcept { return local_days{__to_days()}; }
inline constexpr bool ok() const noexcept { return __y.ok() && __m.ok() && __wdl.ok(); }
constexpr days __to_days() const noexcept;
};
inline constexpr
days year_month_weekday_last::__to_days() const noexcept
{
const sys_days __last = sys_days{__y/__m/last};
return (__last - (chrono::weekday{__last} - __wdl.weekday())).time_since_epoch();
}
inline constexpr
bool operator==(const year_month_weekday_last& __lhs, const year_month_weekday_last& __rhs) noexcept
{ return __lhs.year() == __rhs.year() && __lhs.month() == __rhs.month() && __lhs.weekday_last() == __rhs.weekday_last(); }

View File

@ -0,0 +1,73 @@
//===----------------------------------------------------------------------===//
//
// The LLVM Compiler Infrastructure
//
// This file is dual licensed under the MIT and the University of Illinois Open
// Source Licenses. See LICENSE.TXT for details.
//
//===----------------------------------------------------------------------===//
// UNSUPPORTED: c++98, c++03, c++11, c++14, c++17
// <chrono>
// class weekday;
// constexpr weekday(const local_days& dp) noexcept;
//
// Effects: Constructs an object of type weekday by computing what day
// of the week corresponds to the local_days dp, and representing
// that day of the week in wd_
//
// Remarks: For any value ymd of type year_month_day for which ymd.ok() is true,
// ymd == year_month_day{sys_days{ymd}} is true.
//
// [Example:
// If dp represents 1970-01-01, the constructed weekday represents Thursday by storing 4 in wd_.
// —end example]
#include <chrono>
#include <type_traits>
#include <cassert>
#include "test_macros.h"
int main()
{
using local_days = std::chrono::local_days;
using days = std::chrono::days;
using weekday = std::chrono::weekday;
ASSERT_NOEXCEPT(weekday{std::declval<local_days>()});
{
constexpr local_days sd{}; // 1-Jan-1970 was a Thursday
constexpr weekday wd{sd};
static_assert( wd.ok(), "");
static_assert(static_cast<unsigned>(wd) == 4, "");
}
{
constexpr local_days sd{days{10957+32}}; // 2-Feb-2000 was a Wednesday
constexpr weekday wd{sd};
static_assert( wd.ok(), "");
static_assert(static_cast<unsigned>(wd) == 3, "");
}
{
constexpr local_days sd{days{-10957}}; // 2-Jan-1940 was a Tuesday
constexpr weekday wd{sd};
static_assert( wd.ok(), "");
static_assert(static_cast<unsigned>(wd) == 2, "");
}
{
local_days sd{days{-(10957+34)}}; // 29-Nov-1939 was a Wednesday
weekday wd{sd};
assert( wd.ok());
assert(static_cast<unsigned>(wd) == 3);
}
}

View File

@ -0,0 +1,73 @@
//===----------------------------------------------------------------------===//
//
// The LLVM Compiler Infrastructure
//
// This file is dual licensed under the MIT and the University of Illinois Open
// Source Licenses. See LICENSE.TXT for details.
//
//===----------------------------------------------------------------------===//
// UNSUPPORTED: c++98, c++03, c++11, c++14, c++17
// <chrono>
// class weekday;
// constexpr weekday(const sys_days& dp) noexcept;
//
// Effects: Constructs an object of type weekday by computing what day
// of the week corresponds to the sys_days dp, and representing
// that day of the week in wd_
//
// Remarks: For any value ymd of type year_month_day for which ymd.ok() is true,
// ymd == year_month_day{sys_days{ymd}} is true.
//
// [Example:
// If dp represents 1970-01-01, the constructed weekday represents Thursday by storing 4 in wd_.
// —end example]
#include <chrono>
#include <type_traits>
#include <cassert>
#include "test_macros.h"
int main()
{
using sys_days = std::chrono::sys_days;
using days = std::chrono::days;
using weekday = std::chrono::weekday;
ASSERT_NOEXCEPT(weekday{std::declval<sys_days>()});
{
constexpr sys_days sd{}; // 1-Jan-1970 was a Thursday
constexpr weekday wd{sd};
static_assert( wd.ok(), "");
static_assert(static_cast<unsigned>(wd) == 4, "");
}
{
constexpr sys_days sd{days{10957+32}}; // 2-Feb-2000 was a Wednesday
constexpr weekday wd{sd};
static_assert( wd.ok(), "");
static_assert(static_cast<unsigned>(wd) == 3, "");
}
{
constexpr sys_days sd{days{-10957}}; // 2-Jan-1940 was a Tuesday
constexpr weekday wd{sd};
static_assert( wd.ok(), "");
static_assert(static_cast<unsigned>(wd) == 2, "");
}
{
sys_days sd{days{-(10957+34)}}; // 29-Nov-1939 was a Wednesday
weekday wd{sd};
assert( wd.ok());
assert(static_cast<unsigned>(wd) == 3);
}
}

View File

@ -7,7 +7,6 @@
//
//===----------------------------------------------------------------------===//
// UNSUPPORTED: c++98, c++03, c++11, c++14, c++17
// XFAIL: *
// <chrono>
// class year_month_day;
@ -34,11 +33,53 @@
int main()
{
using year = std::chrono::year;
using month = std::chrono::month;
using day = std::chrono::day;
// using local_days = std::chrono::local_days;
using local_days = std::chrono::local_days;
using days = std::chrono::days;
using year_month_day = std::chrono::year_month_day;
// ASSERT_NOEXCEPT(year_month_day{std::declval<const local_days>()});
assert(false);
ASSERT_NOEXCEPT(year_month_day{std::declval<local_days>()});
{
constexpr local_days sd{};
constexpr year_month_day ymd{sd};
static_assert( ymd.ok(), "");
static_assert( ymd.year() == year{1970}, "");
static_assert( ymd.month() == std::chrono::January, "");
static_assert( ymd.day() == day{1}, "");
}
{
constexpr local_days sd{days{10957+32}};
constexpr year_month_day ymd{sd};
static_assert( ymd.ok(), "");
static_assert( ymd.year() == year{2000}, "");
static_assert( ymd.month() == std::chrono::February, "");
static_assert( ymd.day() == day{2}, "");
}
// There's one more leap day between 1/1/40 and 1/1/70
// when compared to 1/1/70 -> 1/1/2000
{
constexpr local_days sd{days{-10957}};
constexpr year_month_day ymd{sd};
static_assert( ymd.ok(), "");
static_assert( ymd.year() == year{1940}, "");
static_assert( ymd.month() == std::chrono::January, "");
static_assert( ymd.day() == day{2}, "");
}
{
local_days sd{days{-(10957+34)}};
year_month_day ymd{sd};
assert( ymd.ok());
assert( ymd.year() == year{1939});
assert( ymd.month() == std::chrono::November);
assert( ymd.day() == day{29});
}
}

View File

@ -7,15 +7,14 @@
//
//===----------------------------------------------------------------------===//
// UNSUPPORTED: c++98, c++03, c++11, c++14, c++17
// XFAIL: *
// <chrono>
// class year_month_day;
// constexpr year_month_day(const sys_days& dp) noexcept;
//
// Effects: Constructs an object of type year_month_day that corresponds
// to the date represented by dp
// Effects: Constructs an object of type year_month_day that corresponds
// to the date represented by dp.
//
// Remarks: For any value ymd of type year_month_day for which ymd.ok() is true,
// ymd == year_month_day{sys_days{ymd}} is true.
@ -33,12 +32,53 @@
int main()
{
using year = std::chrono::year;
using month = std::chrono::month;
using day = std::chrono::day;
// using sys_days = std::chrono::sys_days;
using sys_days = std::chrono::sys_days;
using days = std::chrono::days;
using year_month_day = std::chrono::year_month_day;
// ASSERT_NOEXCEPT(year_month_day{std::declval<const sys_days>()});
assert(false);
ASSERT_NOEXCEPT(year_month_day{std::declval<sys_days>()});
{
constexpr sys_days sd{};
constexpr year_month_day ymd{sd};
static_assert( ymd.ok(), "");
static_assert( ymd.year() == year{1970}, "");
static_assert( ymd.month() == std::chrono::January, "");
static_assert( ymd.day() == day{1}, "");
}
{
constexpr sys_days sd{days{10957+32}};
constexpr year_month_day ymd{sd};
static_assert( ymd.ok(), "");
static_assert( ymd.year() == year{2000}, "");
static_assert( ymd.month() == std::chrono::February, "");
static_assert( ymd.day() == day{2}, "");
}
// There's one more leap day between 1/1/40 and 1/1/70
// when compared to 1/1/70 -> 1/1/2000
{
constexpr sys_days sd{days{-10957}};
constexpr year_month_day ymd{sd};
static_assert( ymd.ok(), "");
static_assert( ymd.year() == year{1940}, "");
static_assert( ymd.month() == std::chrono::January, "");
static_assert( ymd.day() == day{2}, "");
}
{
sys_days sd{days{-(10957+34)}};
year_month_day ymd{sd};
assert( ymd.ok());
assert( ymd.year() == year{1939});
assert( ymd.month() == std::chrono::November);
assert( ymd.day() == day{29});
}
}

View File

@ -7,7 +7,6 @@
//
//===----------------------------------------------------------------------===//
// UNSUPPORTED: c++98, c++03, c++11, c++14, c++17
// XFAIL: *
// <chrono>
// class year_month_day;
@ -33,10 +32,49 @@ int main()
using year = std::chrono::year;
using month = std::chrono::month;
using day = std::chrono::day;
// using year_month_day_last = std::chrono::year_month_day_last;
using month_day_last = std::chrono::month_day_last;
using year_month_day_last = std::chrono::year_month_day_last;
using year_month_day = std::chrono::year_month_day;
// ASSERT_NOEXCEPT(year_month_day{std::declval<const year_month_day_last>()});
assert(false);
ASSERT_NOEXCEPT(year_month_day{std::declval<const year_month_day_last>()});
{
constexpr year_month_day_last ymdl{year{2019}, month_day_last{month{1}}};
constexpr year_month_day ymd{ymdl};
static_assert( ymd.year() == year{2019}, "");
static_assert( ymd.month() == month{1}, "");
static_assert( ymd.day() == day{31}, "");
static_assert( ymd.ok(), "");
}
{
constexpr year_month_day_last ymdl{year{1970}, month_day_last{month{4}}};
constexpr year_month_day ymd{ymdl};
static_assert( ymd.year() == year{1970}, "");
static_assert( ymd.month() == month{4}, "");
static_assert( ymd.day() == day{30}, "");
static_assert( ymd.ok(), "");
}
{
constexpr year_month_day_last ymdl{year{2000}, month_day_last{month{2}}};
constexpr year_month_day ymd{ymdl};
static_assert( ymd.year() == year{2000}, "");
static_assert( ymd.month() == month{2}, "");
static_assert( ymd.day() == day{29}, "");
static_assert( ymd.ok(), "");
}
{ // Feb 1900 was NOT a leap year.
year_month_day_last ymdl{year{1900}, month_day_last{month{2}}};
year_month_day ymd{ymdl};
assert( ymd.year() == year{1900});
assert( ymd.month() == month{2});
assert( ymd.day() == day{28});
assert( ymd.ok());
}
}

View File

@ -44,6 +44,37 @@ int main()
static_assert( year_month_day{year{2019}, January, day{1}}.ok(), ""); // All OK
// Some months have a 31st
static_assert( year_month_day{year{2020}, month{ 1}, day{31}}.ok(), "");
static_assert(!year_month_day{year{2020}, month{ 2}, day{31}}.ok(), "");
static_assert( year_month_day{year{2020}, month{ 3}, day{31}}.ok(), "");
static_assert(!year_month_day{year{2020}, month{ 4}, day{31}}.ok(), "");
static_assert( year_month_day{year{2020}, month{ 5}, day{31}}.ok(), "");
static_assert(!year_month_day{year{2020}, month{ 6}, day{31}}.ok(), "");
static_assert( year_month_day{year{2020}, month{ 7}, day{31}}.ok(), "");
static_assert( year_month_day{year{2020}, month{ 8}, day{31}}.ok(), "");
static_assert(!year_month_day{year{2020}, month{ 9}, day{31}}.ok(), "");
static_assert( year_month_day{year{2020}, month{10}, day{31}}.ok(), "");
static_assert(!year_month_day{year{2020}, month{11}, day{31}}.ok(), "");
static_assert( year_month_day{year{2020}, month{12}, day{31}}.ok(), "");
// Everyone except FEB has a 30th
static_assert( year_month_day{year{2020}, month{ 1}, day{30}}.ok(), "");
static_assert(!year_month_day{year{2020}, month{ 2}, day{30}}.ok(), "");
static_assert( year_month_day{year{2020}, month{ 3}, day{30}}.ok(), "");
static_assert( year_month_day{year{2020}, month{ 4}, day{30}}.ok(), "");
static_assert( year_month_day{year{2020}, month{ 5}, day{30}}.ok(), "");
static_assert( year_month_day{year{2020}, month{ 6}, day{30}}.ok(), "");
static_assert( year_month_day{year{2020}, month{ 7}, day{30}}.ok(), "");
static_assert( year_month_day{year{2020}, month{ 8}, day{30}}.ok(), "");
static_assert( year_month_day{year{2020}, month{ 9}, day{30}}.ok(), "");
static_assert( year_month_day{year{2020}, month{10}, day{30}}.ok(), "");
static_assert( year_month_day{year{2020}, month{11}, day{30}}.ok(), "");
static_assert( year_month_day{year{2020}, month{12}, day{30}}.ok(), "");
static_assert(!year_month_day{year{2019}, std::chrono::February, day{29}}.ok(), ""); // Not a leap year
static_assert( year_month_day{year{2020}, std::chrono::February, day{29}}.ok(), ""); // Ok; 2020 is a leap year
for (unsigned i = 0; i <= 50; ++i)
{
year_month_day ym{year{2019}, January, day{i}};

View File

@ -0,0 +1,94 @@
//===----------------------------------------------------------------------===//
//
// The LLVM Compiler Infrastructure
//
// This file is dual licensed under the MIT and the University of Illinois Open
// Source Licenses. See LICENSE.TXT for details.
//
//===----------------------------------------------------------------------===//
// UNSUPPORTED: c++98, c++03, c++11, c++14, c++17
// <chrono>
// class year_month_day;
// constexpr operator local_days() const noexcept;
//
// Returns: If ok(), returns a local_days holding a count of days from the
// local_days epoch to *this (a negative value if *this represents a date
// prior to the sys_days epoch). Otherwise, if y_.ok() && m_.ok() is true,
// returns a sys_days which is offset from sys_days{y_/m_/last} by the
// number of days d_ is offset from sys_days{y_/m_/last}.day(). Otherwise
// the value returned is unspecified.
//
// Remarks: A local_days in the range [days{-12687428}, days{11248737}] which
// is converted to a year_month_day shall have the same value when
// converted back to a sys_days.
//
// [Example:
// static_assert(year_month_day{local_days{2017y/January/0}} == 2016y/December/31);
// static_assert(year_month_day{local_days{2017y/January/31}} == 2017y/January/31);
// static_assert(year_month_day{local_days{2017y/January/32}} == 2017y/February/1);
// —end example]
#include <chrono>
#include <type_traits>
#include <cassert>
#include "test_macros.h"
void RunTheExample()
{
using namespace std::chrono;
static_assert(year_month_day{local_days{2017y/January/0}} == 2016y/December/31);
static_assert(year_month_day{local_days{2017y/January/31}} == 2017y/January/31);
static_assert(year_month_day{local_days{2017y/January/32}} == 2017y/February/1);
}
int main()
{
using year = std::chrono::year;
using month = std::chrono::month;
using day = std::chrono::day;
using local_days = std::chrono::local_days;
using days = std::chrono::days;
using year_month_day = std::chrono::year_month_day;
ASSERT_NOEXCEPT(local_days(std::declval<year_month_day>()));
RunTheExample();
{
constexpr year_month_day ymd{year{1970}, month{1}, day{1}};
constexpr local_days sd{ymd};
static_assert( sd.time_since_epoch() == days{0}, "");
static_assert( year_month_day{sd} == ymd, ""); // and back
}
{
constexpr year_month_day ymd{year{2000}, month{2}, day{2}};
constexpr local_days sd{ymd};
static_assert( sd.time_since_epoch() == days{10957+32}, "");
static_assert( year_month_day{sd} == ymd, ""); // and back
}
// There's one more leap day between 1/1/40 and 1/1/70
// when compared to 1/1/70 -> 1/1/2000
{
constexpr year_month_day ymd{year{1940}, month{1}, day{2}};
constexpr local_days sd{ymd};
static_assert( sd.time_since_epoch() == days{-10957}, "");
static_assert( year_month_day{sd} == ymd, ""); // and back
}
{
year_month_day ymd{year{1939}, month{11}, day{29}};
local_days sd{ymd};
assert( sd.time_since_epoch() == days{-(10957+34)});
assert( year_month_day{sd} == ymd); // and back
}
}

View File

@ -0,0 +1,94 @@
//===----------------------------------------------------------------------===//
//
// The LLVM Compiler Infrastructure
//
// This file is dual licensed under the MIT and the University of Illinois Open
// Source Licenses. See LICENSE.TXT for details.
//
//===----------------------------------------------------------------------===//
// UNSUPPORTED: c++98, c++03, c++11, c++14, c++17
// <chrono>
// class year_month_day;
// constexpr operator sys_days() const noexcept;
//
// Returns: If ok(), returns a sys_days holding a count of days from the
// sys_days epoch to *this (a negative value if *this represents a date
// prior to the sys_days epoch). Otherwise, if y_.ok() && m_.ok() is true,
// returns a sys_days which is offset from sys_days{y_/m_/last} by the
// number of days d_ is offset from sys_days{y_/m_/last}.day(). Otherwise
// the value returned is unspecified.
//
// Remarks: A sys_days in the range [days{-12687428}, days{11248737}] which
// is converted to a year_month_day shall have the same value when
// converted back to a sys_days.
//
// [Example:
// static_assert(year_month_day{sys_days{2017y/January/0}} == 2016y/December/31);
// static_assert(year_month_day{sys_days{2017y/January/31}} == 2017y/January/31);
// static_assert(year_month_day{sys_days{2017y/January/32}} == 2017y/February/1);
// —end example]
#include <chrono>
#include <type_traits>
#include <cassert>
#include "test_macros.h"
void RunTheExample()
{
using namespace std::chrono;
static_assert(year_month_day{sys_days{2017y/January/0}} == 2016y/December/31);
static_assert(year_month_day{sys_days{2017y/January/31}} == 2017y/January/31);
static_assert(year_month_day{sys_days{2017y/January/32}} == 2017y/February/1);
}
int main()
{
using year = std::chrono::year;
using month = std::chrono::month;
using day = std::chrono::day;
using sys_days = std::chrono::sys_days;
using days = std::chrono::days;
using year_month_day = std::chrono::year_month_day;
ASSERT_NOEXCEPT(sys_days(std::declval<year_month_day>()));
RunTheExample();
{
constexpr year_month_day ymd{year{1970}, month{1}, day{1}};
constexpr sys_days sd{ymd};
static_assert( sd.time_since_epoch() == days{0}, "");
static_assert( year_month_day{sd} == ymd, ""); // and back
}
{
constexpr year_month_day ymd{year{2000}, month{2}, day{2}};
constexpr sys_days sd{ymd};
static_assert( sd.time_since_epoch() == days{10957+32}, "");
static_assert( year_month_day{sd} == ymd, ""); // and back
}
// There's one more leap day between 1/1/40 and 1/1/70
// when compared to 1/1/70 -> 1/1/2000
{
constexpr year_month_day ymd{year{1940}, month{1}, day{2}};
constexpr sys_days sd{ymd};
static_assert( sd.time_since_epoch() == days{-10957}, "");
static_assert( year_month_day{sd} == ymd, ""); // and back
}
{
year_month_day ymd{year{1939}, month{11}, day{29}};
sys_days sd{ymd};
assert( sd.time_since_epoch() == days{-(10957+34)});
assert( year_month_day{sd} == ymd); // and back
}
}

View File

@ -7,7 +7,6 @@
//
//===----------------------------------------------------------------------===//
// UNSUPPORTED: c++98, c++03, c++11, c++14, c++17
// XFAIL: *
// <chrono>
// class year_month_day_last;
@ -29,15 +28,24 @@ int main()
using month_day_last = std::chrono::month_day_last;
using year_month_day_last = std::chrono::year_month_day_last;
// TODO: wait for calendar
// ASSERT_NOEXCEPT( std::declval<const year_month_day_last>().day());
// ASSERT_SAME_TYPE(day, decltype(std::declval<const year_month_day_last>().day()));
//
// static_assert( year_month_day_last{}.day() == day{}, "");
ASSERT_NOEXCEPT( std::declval<const year_month_day_last>().day());
ASSERT_SAME_TYPE(day, decltype(std::declval<const year_month_day_last>().day()));
for (unsigned i = 1; i <= 12; ++i)
{
year_month_day_last ymd(year{1234}, month_day_last{month{i}});
assert( static_cast<unsigned>(ymd.day()) == i);
}
// Some months have a 31st
static_assert( year_month_day_last{year{2020}, month_day_last{month{ 1}}}.day() == day{31}, "");
static_assert( year_month_day_last{year{2020}, month_day_last{month{ 2}}}.day() == day{29}, "");
static_assert( year_month_day_last{year{2020}, month_day_last{month{ 3}}}.day() == day{31}, "");
static_assert( year_month_day_last{year{2020}, month_day_last{month{ 4}}}.day() == day{30}, "");
static_assert( year_month_day_last{year{2020}, month_day_last{month{ 5}}}.day() == day{31}, "");
static_assert( year_month_day_last{year{2020}, month_day_last{month{ 6}}}.day() == day{30}, "");
static_assert( year_month_day_last{year{2020}, month_day_last{month{ 7}}}.day() == day{31}, "");
static_assert( year_month_day_last{year{2020}, month_day_last{month{ 8}}}.day() == day{31}, "");
static_assert( year_month_day_last{year{2020}, month_day_last{month{ 9}}}.day() == day{30}, "");
static_assert( year_month_day_last{year{2020}, month_day_last{month{10}}}.day() == day{31}, "");
static_assert( year_month_day_last{year{2020}, month_day_last{month{11}}}.day() == day{30}, "");
static_assert( year_month_day_last{year{2020}, month_day_last{month{12}}}.day() == day{31}, "");
assert((year_month_day_last{year{2019}, month_day_last{month{ 2}}}.day() == day{28}));
assert((year_month_day_last{year{2020}, month_day_last{month{ 2}}}.day() == day{29}));
assert((year_month_day_last{year{2021}, month_day_last{month{ 2}}}.day() == day{28}));
}

View File

@ -7,7 +7,6 @@
//
//===----------------------------------------------------------------------===//
// UNSUPPORTED: c++98, c++03, c++11, c++14, c++17
// XFAIL: *
// <chrono>
// class year_month_day_last;
@ -24,13 +23,39 @@
int main()
{
using year = std::chrono::year;
using month = std::chrono::month;
using day = std::chrono::day;
using month_day_last = std::chrono::month_day_last;
using year_month_day_last = std::chrono::year_month_day_last;
// using sys_days = std::chrono::local_days;
using local_days = std::chrono::local_days;
using days = std::chrono::days;
// ASSERT_NOEXCEPT( static_cast<local_days>(std::declval<const year_month_day_last>().year()));
// ASSERT_SAME_TYPE(year, decltype(static_cast<local_days>(std::declval<const year_month_day_last>().year()));
assert(false);
ASSERT_NOEXCEPT( static_cast<local_days>(std::declval<const year_month_day_last>()));
ASSERT_SAME_TYPE(local_days, decltype(static_cast<local_days>(std::declval<const year_month_day_last>())));
{ // Last day in Jan 1970 was the 31st
constexpr year_month_day_last ymdl{year{1970}, month_day_last{std::chrono::January}};
constexpr local_days sd{ymdl};
static_assert(sd.time_since_epoch() == days{30}, "");
}
{
constexpr year_month_day_last ymdl{year{2000}, month_day_last{std::chrono::January}};
constexpr local_days sd{ymdl};
static_assert(sd.time_since_epoch() == days{10957+30}, "");
}
{
constexpr year_month_day_last ymdl{year{1940}, month_day_last{std::chrono::January}};
constexpr local_days sd{ymdl};
static_assert(sd.time_since_epoch() == days{-10957+29}, "");
}
{
year_month_day_last ymdl{year{1939}, month_day_last{std::chrono::November}};
local_days sd{ymdl};
assert(sd.time_since_epoch() == days{-(10957+33)});
}
}

View File

@ -7,7 +7,6 @@
//
//===----------------------------------------------------------------------===//
// UNSUPPORTED: c++98, c++03, c++11, c++14, c++17
// XFAIL: *
// <chrono>
// class year_month_day_last;
@ -24,13 +23,39 @@
int main()
{
using year = std::chrono::year;
using month = std::chrono::month;
using day = std::chrono::day;
using month_day_last = std::chrono::month_day_last;
using year_month_day_last = std::chrono::year_month_day_last;
// using sys_days = std::chrono::sys_days;
using sys_days = std::chrono::sys_days;
using days = std::chrono::days;
// ASSERT_NOEXCEPT( static_cast<sys_days>(std::declval<const year_month_day_last>().year()));
// ASSERT_SAME_TYPE(year, decltype(static_cast<sys_days>(std::declval<const year_month_day_last>().year()));
assert(false);
ASSERT_NOEXCEPT( static_cast<sys_days>(std::declval<const year_month_day_last>()));
ASSERT_SAME_TYPE(sys_days, decltype(static_cast<sys_days>(std::declval<const year_month_day_last>())));
{ // Last day in Jan 1970 was the 31st
constexpr year_month_day_last ymdl{year{1970}, month_day_last{std::chrono::January}};
constexpr sys_days sd{ymdl};
static_assert(sd.time_since_epoch() == days{30}, "");
}
{
constexpr year_month_day_last ymdl{year{2000}, month_day_last{std::chrono::January}};
constexpr sys_days sd{ymdl};
static_assert(sd.time_since_epoch() == days{10957+30}, "");
}
{
constexpr year_month_day_last ymdl{year{1940}, month_day_last{std::chrono::January}};
constexpr sys_days sd{ymdl};
static_assert(sd.time_since_epoch() == days{-10957+29}, "");
}
{
year_month_day_last ymdl{year{1939}, month_day_last{std::chrono::November}};
sys_days sd{ymdl};
assert(sd.time_since_epoch() == days{-(10957+33)});
}
}

View File

@ -7,7 +7,6 @@
//
//===----------------------------------------------------------------------===//
// UNSUPPORTED: c++98, c++03, c++11, c++14, c++17
// XFAIL: *
// <chrono>
// class year_month_weekday;
@ -33,12 +32,64 @@
int main()
{
using year = std::chrono::year;
using month = std::chrono::month;
using day = std::chrono::day;
// using local_days = std::chrono::local_days;
using year = std::chrono::year;
using days = std::chrono::days;
using local_days = std::chrono::local_days;
using weekday_indexed = std::chrono::weekday_indexed;
using year_month_weekday = std::chrono::year_month_weekday;
// ASSERT_NOEXCEPT(year_month_weekday{std::declval<const local_days>()});
assert(false);
ASSERT_NOEXCEPT(year_month_weekday{std::declval<const local_days>()});
{
constexpr local_days sd{}; // 1-Jan-1970 was a Thursday
constexpr year_month_weekday ymwd{sd};
static_assert( ymwd.ok(), "");
static_assert( ymwd.year() == year{1970}, "");
static_assert( ymwd.month() == std::chrono::January, "");
static_assert( ymwd.weekday() == std::chrono::Thursday, "");
static_assert( ymwd.index() == 1, "");
static_assert( ymwd.weekday_indexed() == weekday_indexed{std::chrono::Thursday, 1}, "");
static_assert( ymwd == year_month_weekday{local_days{ymwd}}, ""); // round trip
}
{
constexpr local_days sd{days{10957+32}}; // 2-Feb-2000 was a Wednesday
constexpr year_month_weekday ymwd{sd};
static_assert( ymwd.ok(), "");
static_assert( ymwd.year() == year{2000}, "");
static_assert( ymwd.month() == std::chrono::February, "");
static_assert( ymwd.weekday() == std::chrono::Wednesday, "");
static_assert( ymwd.index() == 1, "");
static_assert( ymwd.weekday_indexed() == weekday_indexed{std::chrono::Wednesday, 1}, "");
static_assert( ymwd == year_month_weekday{local_days{ymwd}}, ""); // round trip
}
{
constexpr local_days sd{days{-10957}}; // 2-Jan-1940 was a Tuesday
constexpr year_month_weekday ymwd{sd};
static_assert( ymwd.ok(), "");
static_assert( ymwd.year() == year{1940}, "");
static_assert( ymwd.month() == std::chrono::January, "");
static_assert( ymwd.weekday() == std::chrono::Tuesday, "");
static_assert( ymwd.index() == 1, "");
static_assert( ymwd.weekday_indexed() == weekday_indexed{std::chrono::Tuesday, 1}, "");
static_assert( ymwd == year_month_weekday{local_days{ymwd}}, ""); // round trip
}
{
local_days sd{days{-(10957+34)}}; // 29-Nov-1939 was a Wednesday
year_month_weekday ymwd{sd};
assert( ymwd.ok());
assert( ymwd.year() == year{1939});
assert( ymwd.month() == std::chrono::November);
assert( ymwd.weekday() == std::chrono::Wednesday);
assert( ymwd.index() == 5);
assert((ymwd.weekday_indexed() == weekday_indexed{std::chrono::Wednesday, 5}));
assert( ymwd == year_month_weekday{local_days{ymwd}}); // round trip
}
}

View File

@ -7,7 +7,6 @@
//
//===----------------------------------------------------------------------===//
// UNSUPPORTED: c++98, c++03, c++11, c++14, c++17
// XFAIL: *
// <chrono>
// class year_month_weekday;
@ -32,12 +31,64 @@
int main()
{
using year = std::chrono::year;
using month = std::chrono::month;
using day = std::chrono::day;
// using sys_days = std::chrono::sys_days;
using year = std::chrono::year;
using days = std::chrono::days;
using sys_days = std::chrono::sys_days;
using weekday_indexed = std::chrono::weekday_indexed;
using year_month_weekday = std::chrono::year_month_weekday;
// ASSERT_NOEXCEPT(year_month_weekday{std::declval<const sys_days>()});
assert(false);
ASSERT_NOEXCEPT(year_month_weekday{std::declval<const sys_days>()});
{
constexpr sys_days sd{}; // 1-Jan-1970 was a Thursday
constexpr year_month_weekday ymwd{sd};
static_assert( ymwd.ok(), "");
static_assert( ymwd.year() == year{1970}, "");
static_assert( ymwd.month() == std::chrono::January, "");
static_assert( ymwd.weekday() == std::chrono::Thursday, "");
static_assert( ymwd.index() == 1, "");
static_assert( ymwd.weekday_indexed() == weekday_indexed{std::chrono::Thursday, 1}, "");
static_assert( ymwd == year_month_weekday{sys_days{ymwd}}, ""); // round trip
}
{
constexpr sys_days sd{days{10957+32}}; // 2-Feb-2000 was a Wednesday
constexpr year_month_weekday ymwd{sd};
static_assert( ymwd.ok(), "");
static_assert( ymwd.year() == year{2000}, "");
static_assert( ymwd.month() == std::chrono::February, "");
static_assert( ymwd.weekday() == std::chrono::Wednesday, "");
static_assert( ymwd.index() == 1, "");
static_assert( ymwd.weekday_indexed() == weekday_indexed{std::chrono::Wednesday, 1}, "");
static_assert( ymwd == year_month_weekday{sys_days{ymwd}}, ""); // round trip
}
{
constexpr sys_days sd{days{-10957}}; // 2-Jan-1940 was a Tuesday
constexpr year_month_weekday ymwd{sd};
static_assert( ymwd.ok(), "");
static_assert( ymwd.year() == year{1940}, "");
static_assert( ymwd.month() == std::chrono::January, "");
static_assert( ymwd.weekday() == std::chrono::Tuesday, "");
static_assert( ymwd.index() == 1, "");
static_assert( ymwd.weekday_indexed() == weekday_indexed{std::chrono::Tuesday, 1}, "");
static_assert( ymwd == year_month_weekday{sys_days{ymwd}}, ""); // round trip
}
{
sys_days sd{days{-(10957+34)}}; // 29-Nov-1939 was a Wednesday
year_month_weekday ymwd{sd};
assert( ymwd.ok());
assert( ymwd.year() == year{1939});
assert( ymwd.month() == std::chrono::November);
assert( ymwd.weekday() == std::chrono::Wednesday);
assert( ymwd.index() == 5);
assert((ymwd.weekday_indexed() == weekday_indexed{std::chrono::Wednesday, 5}));
assert( ymwd == year_month_weekday{sys_days{ymwd}}); // round trip
}
}

View File

@ -1,41 +0,0 @@
//===----------------------------------------------------------------------===//
//
// The LLVM Compiler Infrastructure
//
// This file is dual licensed under the MIT and the University of Illinois Open
// Source Licenses. See LICENSE.TXT for details.
//
//===----------------------------------------------------------------------===//
// UNSUPPORTED: c++98, c++03, c++11, c++14, c++17
// XFAIL: *
// <chrono>
// class year_month_weekday;
// constexpr year_month_weekday(const year_month_weekday_last& ymdl) noexcept;
//
// Effects: Constructs an object of type year_month_weekday by initializing
// y_ with ymdl.year(), m_ with ymdl.month(), and d_ with ymdl.day().
//
// constexpr chrono::year year() const noexcept;
// constexpr chrono::month month() const noexcept;
// constexpr chrono::day day() const noexcept;
// constexpr bool ok() const noexcept;
#include <chrono>
#include <type_traits>
#include <cassert>
#include "test_macros.h"
int main()
{
using year = std::chrono::year;
using month = std::chrono::month;
using day = std::chrono::day;
using year_month_weekday_last = std::chrono::year_month_weekday_last;
using year_month_weekday = std::chrono::year_month_weekday;
ASSERT_NOEXCEPT(year_month_weekday{std::declval<const year_month_weekday_last>()});
}

View File

@ -0,0 +1,74 @@
//===----------------------------------------------------------------------===//
//
// The LLVM Compiler Infrastructure
//
// This file is dual licensed under the MIT and the University of Illinois Open
// Source Licenses. See LICENSE.TXT for details.
//
//===----------------------------------------------------------------------===//
// UNSUPPORTED: c++98, c++03, c++11, c++14, c++17
// <chrono>
// class year_month_weekday;
// explicit constexpr operator local_days() const noexcept;
//
// Returns: If y_.ok() && m_.ok() && wdi_.weekday().ok(), returns a
// sys_days that represents the date (index() - 1) * 7 days after the first
// weekday() of year()/month(). If index() is 0 the returned sys_days
// represents the date 7 days prior to the first weekday() of
// year()/month(). Otherwise the returned value is unspecified.
//
#include <chrono>
#include <type_traits>
#include <cassert>
#include "test_macros.h"
int main()
{
using year = std::chrono::year;
using month = std::chrono::month;
using weekday_indexed = std::chrono::weekday_indexed;
using local_days = std::chrono::local_days;
using days = std::chrono::days;
using year_month_weekday = std::chrono::year_month_weekday;
ASSERT_NOEXCEPT(local_days(std::declval<year_month_weekday>()));
{
constexpr year_month_weekday ymwd{year{1970}, month{1}, weekday_indexed{std::chrono::Thursday, 1}};
constexpr local_days sd{ymwd};
static_assert( sd.time_since_epoch() == days{0}, "");
static_assert( year_month_weekday{sd} == ymwd, ""); // and back
}
{
constexpr year_month_weekday ymwd{year{2000}, month{2}, weekday_indexed{std::chrono::Wednesday, 1}};
constexpr local_days sd{ymwd};
static_assert( sd.time_since_epoch() == days{10957+32}, "");
static_assert( year_month_weekday{sd} == ymwd, ""); // and back
}
// There's one more leap day between 1/1/40 and 1/1/70
// when compared to 1/1/70 -> 1/1/2000
{
constexpr year_month_weekday ymwd{year{1940}, month{1},weekday_indexed{std::chrono::Tuesday, 1}};
constexpr local_days sd{ymwd};
static_assert( sd.time_since_epoch() == days{-10957}, "");
static_assert( year_month_weekday{sd} == ymwd, ""); // and back
}
{
year_month_weekday ymwd{year{1939}, month{11}, weekday_indexed{std::chrono::Wednesday, 5}};
local_days sd{ymwd};
assert( sd.time_since_epoch() == days{-(10957+34)});
assert( year_month_weekday{sd} == ymwd); // and back
}
}

View File

@ -0,0 +1,74 @@
//===----------------------------------------------------------------------===//
//
// The LLVM Compiler Infrastructure
//
// This file is dual licensed under the MIT and the University of Illinois Open
// Source Licenses. See LICENSE.TXT for details.
//
//===----------------------------------------------------------------------===//
// UNSUPPORTED: c++98, c++03, c++11, c++14, c++17
// <chrono>
// class year_month_weekday;
// constexpr operator sys_days() const noexcept;
//
// Returns: If y_.ok() && m_.ok() && wdi_.weekday().ok(), returns a
// sys_days that represents the date (index() - 1) * 7 days after the first
// weekday() of year()/month(). If index() is 0 the returned sys_days
// represents the date 7 days prior to the first weekday() of
// year()/month(). Otherwise the returned value is unspecified.
//
#include <chrono>
#include <type_traits>
#include <cassert>
#include "test_macros.h"
int main()
{
using year = std::chrono::year;
using month = std::chrono::month;
using weekday_indexed = std::chrono::weekday_indexed;
using sys_days = std::chrono::sys_days;
using days = std::chrono::days;
using year_month_weekday = std::chrono::year_month_weekday;
ASSERT_NOEXCEPT(sys_days(std::declval<year_month_weekday>()));
{
constexpr year_month_weekday ymwd{year{1970}, month{1}, weekday_indexed{std::chrono::Thursday, 1}};
constexpr sys_days sd{ymwd};
static_assert( sd.time_since_epoch() == days{0}, "");
static_assert( year_month_weekday{sd} == ymwd, ""); // and back
}
{
constexpr year_month_weekday ymwd{year{2000}, month{2}, weekday_indexed{std::chrono::Wednesday, 1}};
constexpr sys_days sd{ymwd};
static_assert( sd.time_since_epoch() == days{10957+32}, "");
static_assert( year_month_weekday{sd} == ymwd, ""); // and back
}
// There's one more leap day between 1/1/40 and 1/1/70
// when compared to 1/1/70 -> 1/1/2000
{
constexpr year_month_weekday ymwd{year{1940}, month{1},weekday_indexed{std::chrono::Tuesday, 1}};
constexpr sys_days sd{ymwd};
static_assert( sd.time_since_epoch() == days{-10957}, "");
static_assert( year_month_weekday{sd} == ymwd, ""); // and back
}
{
year_month_weekday ymwd{year{1939}, month{11}, weekday_indexed{std::chrono::Wednesday, 5}};
sys_days sd{ymwd};
assert( sd.time_since_epoch() == days{-(10957+34)});
assert( year_month_weekday{sd} == ymwd); // and back
}
}

View File

@ -7,7 +7,6 @@
//
//===----------------------------------------------------------------------===//
// UNSUPPORTED: c++98, c++03, c++11, c++14, c++17
// XFAIL: *
// <chrono>
// class year_month_day_last;
@ -24,12 +23,39 @@
int main()
{
using year = std::chrono::year;
using month = std::chrono::month;
using day = std::chrono::day;
using month_day_last = std::chrono::month_day_last;
using year_month_day_last = std::chrono::year_month_day_last;
using sys_days = std::chrono::local_days;
using local_days = std::chrono::local_days;
using days = std::chrono::days;
ASSERT_NOEXCEPT( static_cast<local_days>(std::declval<const year_month_day_last>().year()));
ASSERT_SAME_TYPE(year, decltype(static_cast<local_days>(std::declval<const year_month_day_last>().year()));
ASSERT_NOEXCEPT( static_cast<local_days>(std::declval<const year_month_day_last>()));
ASSERT_SAME_TYPE(local_days, decltype(static_cast<local_days>(std::declval<const year_month_day_last>())));
{ // Last day in Jan 1970 was the 31st
constexpr year_month_day_last ymdl{year{1970}, month_day_last{std::chrono::January}};
constexpr local_days sd{ymdl};
static_assert(sd.time_since_epoch() == days{30}, "");
}
{
constexpr year_month_day_last ymdl{year{2000}, month_day_last{std::chrono::January}};
constexpr local_days sd{ymdl};
static_assert(sd.time_since_epoch() == days{10957+30}, "");
}
{
constexpr year_month_day_last ymdl{year{1940}, month_day_last{std::chrono::January}};
constexpr local_days sd{ymdl};
static_assert(sd.time_since_epoch() == days{-10957+29}, "");
}
{
year_month_day_last ymdl{year{1939}, month_day_last{std::chrono::November}};
local_days sd{ymdl};
assert(sd.time_since_epoch() == days{-(10957+33)});
}
}

View File

@ -7,13 +7,13 @@
//
//===----------------------------------------------------------------------===//
// UNSUPPORTED: c++98, c++03, c++11, c++14, c++17
// XFAIL: *
// <chrono>
// class year_month_day_last;
// class year_month_weekday_last;
// constexpr operator sys_days() const noexcept;
// Returns: sys_days{year()/month()/day()}.
// Returns: If ok() == true, returns a sys_days that represents the last weekday()
// of year()/month(). Otherwise the returned value is unspecified.
#include <chrono>
#include <type_traits>
@ -21,16 +21,49 @@
#include "test_macros.h"
#include <iostream>
int main()
{
using year = std::chrono::year;
using month = std::chrono::month;
using day = std::chrono::day;
using month_day_last = std::chrono::month_day_last;
using year_month_day_last = std::chrono::year_month_day_last;
using sys_days = std::chrono::sys_days;
using year = std::chrono::year;
using month = std::chrono::month;
using year_month_weekday_last = std::chrono::year_month_weekday_last;
using sys_days = std::chrono::sys_days;
using days = std::chrono::days;
using weekday = std::chrono::weekday;
using weekday_last = std::chrono::weekday_last;
ASSERT_NOEXCEPT( static_cast<sys_days>(std::declval<const year_month_day_last>().year()));
ASSERT_SAME_TYPE(year, decltype(static_cast<sys_days>(std::declval<const year_month_day_last>().year()));
ASSERT_NOEXCEPT( static_cast<sys_days>(std::declval<const year_month_weekday_last>()));
ASSERT_SAME_TYPE(sys_days, decltype(static_cast<sys_days>(std::declval<const year_month_weekday_last>())));
constexpr month January = std::chrono::January;
constexpr weekday Tuesday = std::chrono::Tuesday;
{ // Last Tuesday in Jan 1970 was the 27th
constexpr year_month_weekday_last ymwdl{year{1970}, January, weekday_last{Tuesday}};
constexpr sys_days sd{ymwdl};
static_assert(sd.time_since_epoch() == days{26}, "");
}
{ // Last Tuesday in Jan 2000 was the 25th
constexpr year_month_weekday_last ymwdl{year{2000}, January, weekday_last{Tuesday}};
constexpr sys_days sd{ymwdl};
static_assert(sd.time_since_epoch() == days{10957+24}, "");
}
{ // Last Tuesday in Jan 1940 was the 30th
constexpr year_month_weekday_last ymwdl{year{1940}, January, weekday_last{Tuesday}};
constexpr sys_days sd{ymwdl};
static_assert(sd.time_since_epoch() == days{-10958+29}, "");
}
{ // Last Tuesday in Nov 1939 was the 28th
year_month_weekday_last ymdl{year{1939}, std::chrono::November, weekday_last{Tuesday}};
sys_days sd{ymdl};
assert(sd.time_since_epoch() == days{-(10957+35)});
}
}

View File

@ -0,0 +1,65 @@
//===----------------------------------------------------------------------===//
//
// The LLVM Compiler Infrastructure
//
// This file is dual licensed under the MIT and the University of Illinois Open
// Source Licenses. See LICENSE.TXT for details.
//
//===----------------------------------------------------------------------===//
// UNSUPPORTED: c++98, c++03, c++11, c++14, c++17
// <chrono>
// struct local_t {};
// template<class Duration>
// using local_time = time_point<system_clock, Duration>;
// using local_seconds = sys_time<seconds>;
// using local_days = sys_time<days>;
// [Example:
// sys_seconds{sys_days{1970y/January/1}}.time_since_epoch() is 0s.
// sys_seconds{sys_days{2000y/January/1}}.time_since_epoch() is 946684800s, which is 10957 * 86400s.
// —end example]
#include <chrono>
#include <cassert>
#include "test_macros.h"
int main()
{
using local_t = std::chrono::local_t;
using year = std::chrono::year;
using seconds = std::chrono::seconds;
using minutes = std::chrono::minutes;
using days = std::chrono::days;
using local_seconds = std::chrono::local_seconds;
using local_minutes = std::chrono::local_time<minutes>;
using local_days = std::chrono::local_days;
constexpr std::chrono::month January = std::chrono::January;
ASSERT_SAME_TYPE(std::chrono::local_time<seconds>, local_seconds);
ASSERT_SAME_TYPE(std::chrono::local_time<days>, local_days);
// Test the long form, too
ASSERT_SAME_TYPE(std::chrono::time_point<local_t, seconds>, local_seconds);
ASSERT_SAME_TYPE(std::chrono::time_point<local_t, minutes>, local_minutes);
ASSERT_SAME_TYPE(std::chrono::time_point<local_t, days>, local_days);
// Test some well known values
local_days d0 = local_days{year{1970}/January/1};
local_days d1 = local_days{year{2000}/January/1};
ASSERT_SAME_TYPE(decltype(d0.time_since_epoch()), days);
assert( d0.time_since_epoch().count() == 0);
assert( d1.time_since_epoch().count() == 10957);
local_seconds s0{d0};
local_seconds s1{d1};
ASSERT_SAME_TYPE(decltype(s0.time_since_epoch()), seconds);
assert( s0.time_since_epoch().count() == 0);
assert( s1.time_since_epoch().count() == 946684800L);
}

View File

@ -0,0 +1,64 @@
//===----------------------------------------------------------------------===//
//
// The LLVM Compiler Infrastructure
//
// This file is dual licensed under the MIT and the University of Illinois Open
// Source Licenses. See LICENSE.TXT for details.
//
//===----------------------------------------------------------------------===//
// UNSUPPORTED: c++98, c++03, c++11, c++14, c++17
// <chrono>
// template<class Duration>
// using sys_time = time_point<system_clock, Duration>;
// using sys_seconds = sys_time<seconds>;
// using sys_days = sys_time<days>;
// [Example:
// sys_seconds{sys_days{1970y/January/1}}.time_since_epoch() is 0s.
// sys_seconds{sys_days{2000y/January/1}}.time_since_epoch() is 946684800s, which is 10957 * 86400s.
// —end example]
#include <chrono>
#include <cassert>
#include "test_macros.h"
int main()
{
using system_clock = std::chrono::system_clock;
using year = std::chrono::year;
using seconds = std::chrono::seconds;
using minutes = std::chrono::minutes;
using days = std::chrono::days;
using sys_seconds = std::chrono::sys_seconds;
using sys_minutes = std::chrono::sys_time<minutes>;
using sys_days = std::chrono::sys_days;
constexpr std::chrono::month January = std::chrono::January;
ASSERT_SAME_TYPE(std::chrono::sys_time<seconds>, sys_seconds);
ASSERT_SAME_TYPE(std::chrono::sys_time<days>, sys_days);
// Test the long form, too
ASSERT_SAME_TYPE(std::chrono::time_point<system_clock, seconds>, sys_seconds);
ASSERT_SAME_TYPE(std::chrono::time_point<system_clock, minutes>, sys_minutes);
ASSERT_SAME_TYPE(std::chrono::time_point<system_clock, days>, sys_days);
// Test some well known values
sys_days d0 = sys_days{year{1970}/January/1};
sys_days d1 = sys_days{year{2000}/January/1};
ASSERT_SAME_TYPE(decltype(d0.time_since_epoch()), days);
assert( d0.time_since_epoch().count() == 0);
assert( d1.time_since_epoch().count() == 10957);
sys_seconds s0{d0};
sys_seconds s1{d1};
ASSERT_SAME_TYPE(decltype(s0.time_since_epoch()), seconds);
assert( s0.time_since_epoch().count() == 0);
assert( s1.time_since_epoch().count() == 946684800L);
}