diff --git a/doc/date_algorithms.html b/doc/date_algorithms.html index f650355..dff45fb 100644 --- a/doc/date_algorithms.html +++ b/doc/date_algorithms.html @@ -71,10 +71,11 @@ Date algorithms or generators are tools for generating other dates or schedules Calculate something like first Monday of January first_kday_of_month fkm(Monday,Jan);
date d = fkm.get_date(2002);//2002-Jan-07 partial_date - greg_month month
greg_day day_of_month + greg_day day_of_month
+ greg_month month greg_year year Generates a date by applying the year to the given month and day. - partial_date pd(Jan,1);
date d = pd.get_date(2002);//2002-Jan-01 + partial_date pd(1,Jan);
date d = pd.get_date(2002);//2002-Jan-01 @@ -84,7 +85,7 @@ Date algorithms or generators are tools for generating other dates or schedules
-Last modified: Tue Sep 3 16:02:55 MST 2002 +Last modified: Fri Nov 29 19:40:48 MST 2002 by Jeff Garland © 2000-2002
diff --git a/doc/exp-print_holidays.html b/doc/exp-print_holidays.html index 97b51d6..4352b93 100644 --- a/doc/exp-print_holidays.html +++ b/doc/exp-print_holidays.html @@ -50,9 +50,9 @@ main() { //define a collection of holidays fixed by month and day std::vector<partial_date> holidays; - holidays.push_back(partial_date(Jan,1)); //Western New Year - holidays.push_back(partial_date(Jul,4)); //US Independence Day - holidays.push_back(partial_date(Dec,25));//Christmas day + holidays.push_back(partial_date(1, Jan)); //Western New Year + holidays.push_back(partial_date(4, Jul)); //US Independence Day + holidays.push_back(partial_date(25, Dec));//Christmas day //define a shorthand for the nkday function object diff --git a/example/gregorian/print_holidays.cpp b/example/gregorian/print_holidays.cpp index a991b11..7aef8d2 100644 --- a/example/gregorian/print_holidays.cpp +++ b/example/gregorian/print_holidays.cpp @@ -39,9 +39,9 @@ main() { //define a collection of holidays fixed by month and day std::vector holidays; - holidays.push_back(partial_date(Jan,1)); //Western New Year - holidays.push_back(partial_date(Jul,4)); //US Independence Day - holidays.push_back(partial_date(Dec,25));//Christmas day + holidays.push_back(partial_date(1,Jan)); //Western New Year + holidays.push_back(partial_date(4,Jul)); //US Independence Day + holidays.push_back(partial_date(25, Dec));//Christmas day //define a shorthand for the nkday function object diff --git a/include/boost/date_time/date_defs.hpp b/include/boost/date_time/date_defs.hpp index ae65d20..539b581 100644 --- a/include/boost/date_time/date_defs.hpp +++ b/include/boost/date_time/date_defs.hpp @@ -14,6 +14,9 @@ namespace date_time { //! An enumeration of weekday names enum weekdays {Sunday, Monday, Tuesday, Wednesday, Thursday, Friday, Saturday}; + //! Simple enum to allow for nice programming with Jan, Feb, etc + enum months_of_year {Jan=1,Feb,Mar,Apr,May,Jun,Jul,Aug,Sep,Oct,Nov,Dec,NotAMonth,NumMonths}; + } } //namespace date_time /* Copyright (c) 2000,2002 diff --git a/include/boost/date_time/date_generators.hpp b/include/boost/date_time/date_generators.hpp index 5564904..781d7f2 100644 --- a/include/boost/date_time/date_generators.hpp +++ b/include/boost/date_time/date_generators.hpp @@ -16,12 +16,12 @@ namespace date_time { //! Generates a date by applying the year to the given month and day. /*! - *Example usage: - *@code - * partial_date pd(Jan,1); - * date d = pd.get_date(2002);//2002-Jan-01 - *@endcode - * \ingroup date_alg + Example usage: + @code + partial_date pd(1, Jan); + date d = pd.get_date(2002); //2002-Jan-01 + @endcode + \ingroup date_alg */ template class partial_date { @@ -31,9 +31,9 @@ namespace date_time { typedef typename calendar_type::month_type month_type; typedef typename calendar_type::year_type year_type; typedef typename date_type::duration_type duration_type; - partial_date(month_type m, day_type d) : - month_(m), - day_(d) + partial_date(day_type d, month_type m) : + day_(d), + month_(m) {} //! Return a concrete date when provided with a year specific year. date_type get_date(year_type y) const @@ -44,11 +44,22 @@ namespace date_time { { return date_type(y, month_, day_); } + bool operator==(const partial_date& rhs) const + { + return (month_ == rhs.month_) && (day_ == rhs.day_); + } + bool operator<(const partial_date& rhs) const + { + if (month_ < rhs.month_) return true; + if (month_ > rhs.month_) return false; + //months are equal + return (day_ < rhs.day_); + } private: - month_type month_; day_type day_; + month_type month_; }; @@ -144,6 +155,7 @@ namespace date_time { /*! Useful generator functor for finding holidays and daylight savings * Get the last day of the month and then calculate the difference * to the last previous day. + * @param date_type A date class that exports day_of_week, month_type, etc. * \ingroup date_alg */ template @@ -154,7 +166,7 @@ namespace date_time { typedef typename calendar_type::month_type month_type; typedef typename calendar_type::year_type year_type; typedef typename date_type::duration_type duration_type; - //!Specify the date spec like 'Sunday' in 'April' spec + //!Specify the date spec like last 'Sunday' in 'April' spec /*!@param dow The day of week, eg: Sunday, Monday, etc * @param month The month of the year, eg: Jan, Feb, Mar, etc */ diff --git a/include/boost/date_time/dst_rules.hpp b/include/boost/date_time/dst_rules.hpp index edde553..e90111f 100644 --- a/include/boost/date_time/dst_rules.hpp +++ b/include/boost/date_time/dst_rules.hpp @@ -21,7 +21,7 @@ namespace boost { ambiguous, invalid_time_label}; - //! Generic functions to calculate dst transition information + //! Dynamic class used to caluclate dst transition information template class dst_calculator @@ -90,7 +90,7 @@ namespace boost { * @param dst_start_offset_minutes Offset within day for dst * boundary (eg 120 for US which is 02:00:00) * @param dst_end_day Ending day of dst for the given locality - * @param dst_end_offset_minutes Offset within day for dst + * @param dst_end_offset_minutes Offset within day given in dst for dst * boundary (eg 120 for US which is 02:00:00) * @param dst_length_minutes Length of dst adjusment (eg: 60 for US) * @retval The time is either ambiguous, invalid, in dst, or not in dst @@ -140,14 +140,104 @@ namespace boost { }; - //! Class to calculate dst boundaries for US time zones - /* + //! Compile-time configurable daylight savings time calculation engine + /* This template provides the ability to configure a daylight savings + * calculation at compile time covering all the cases. Unfortunately + * because of the number of dimensions related to daylight savings + * calculation the number of parameters is high. In addition, the + * start and end transition rules are complex types that specify + * an algorithm for calculation of the starting day and ending + * day of daylight savings time including the month and day + * specifications (eg: last sunday in October). + * + * @param date_type A type that represents dates, typically gregorian::date + * @param time_duration_type Used for the offset in the day calculations + * @param dst_traits A set of traits that define the rules of dst + * calculation. The dst_trait must include the following: + * start_rule_functor - Rule to calculate the starting date of a + * dst transition (eg: last_kday_of_month). + * start_day - static function that returns month of dst start for + * start_rule_functor + * start_month -static function that returns day or day of week for + * dst start of dst + * end_rule_functor - Rule to calculate the end of dst day. + * end_day - static fucntion that returns end day for end_rule_functor + * end_month - static function that returns end month for end_rule_functor + * dst_start_offset_minutes - number of minutes from start of day to transition to dst -- 120 (or 2:00 am) is typical for the U.S. and E.U. + * dst_start_offset_minutes - number of minutes from start of day to transition off of dst -- 180 (or 3:00 am) is typical for E.U. + * dst_length_minutes - number of minutes that dst shifts clock + */ + template + class dst_calc_engine + { + public: + typedef typename date_type::year_type year_type; + typedef typename date_type::calendar_type calendar_type; + typedef dst_calculator dstcalc; + + //! Calculates if the given local time is dst or not + /*! Determines if the time is really in DST or not. Also checks for + * invalid and ambiguous. + * @retval The time is either ambiguous, invalid, in dst, or not in dst + */ + static time_is_dst_result local_is_dst(const date_type& d, + const time_duration_type& td) + { + + year_type y = d.year(); + date_type dst_start = local_dst_start_day(y); + date_type dst_end = local_dst_end_day(y); + return dstcalc::local_is_dst(d,td, + dst_start, + dst_traits::dst_start_offset_minutes(), + dst_end, + dst_traits::dst_end_offset_minutes(), + dst_traits::dst_shift_length_minutes()); + + } + + static bool is_dst_boundary_day(date_type d) + { + year_type y = d.year(); + return ((d == local_dst_start_day(y)) || + (d == local_dst_end_day(y))); + } + + //! The time of day for the dst transition (eg: typically 01:00:00 or 02:00:00) + static time_duration_type dst_offset() + { + return time_duration_type(0,dst_traits::dst_shift_length_minutes(),0); + } + + static date_type local_dst_start_day(year_type year) + { + typedef typename dst_traits::start_rule_functor start_rule; + start_rule start(dst_traits::start_day(), + dst_traits::start_month()); + return start.get_date(year); + } + + static date_type local_dst_end_day(year_type year) + { + typedef typename dst_traits::end_rule_functor end_rule; + end_rule end(dst_traits::end_day(), + dst_traits::end_month()); + return end.get_date(year); + } + + + }; + + //! Depricated: Class to calculate dst boundaries for US time zones + /* Use dst_calc_engine instead. */ template //1 hour == 60 min in US - class us_dst_rules + class us_dst_rules { public: typedef time_duration_type_ time_duration_type; @@ -199,15 +289,14 @@ namespace boost { return lsio.get_date(year); } - static time_duration_type dst_offset() + static time_duration_type dst_offset() { return time_duration_type(0,dst_length_minutes,0); } + }; - - //! Used for local time adjustments in places that don't use dst template class null_dst_rules diff --git a/include/boost/date_time/gregorian/greg_month.hpp b/include/boost/date_time/gregorian/greg_month.hpp index f086a0d..0a9ba52 100644 --- a/include/boost/date_time/gregorian/greg_month.hpp +++ b/include/boost/date_time/gregorian/greg_month.hpp @@ -6,6 +6,7 @@ */ #include "boost/date_time/constrained_value.hpp" +#include "boost/date_time/date_defs.hpp" #include #include @@ -13,9 +14,23 @@ namespace boost { namespace gregorian { + typedef date_time::months_of_year months_of_year; - //! Simple enum to allow for nice programming with Jan, Feb, etc - enum months_of_year {Jan=1,Feb,Mar,Apr,May,Jun,Jul,Aug,Sep,Oct,Nov,Dec,NotAMonth,NumMonths}; + //bring enum values into the namespace + using date_time::Jan; + using date_time::Feb; + using date_time::Mar; + using date_time::Apr; + using date_time::May; + using date_time::Jun; + using date_time::Jul; + using date_time::Aug; + using date_time::Sep; + using date_time::Oct; + using date_time::Nov; + using date_time::Dec; + using date_time::NotAMonth; + using date_time::NumMonths; //! Exception thrown if a greg_month is constructed with a value out of range struct bad_month : public std::out_of_range @@ -31,9 +46,9 @@ namespace gregorian { //! Wrapper class to represent months in gregorian based calendar class greg_month : public greg_month_rep { public: - typedef months_of_year month_enum; + typedef date_time::months_of_year month_enum; //! Construct a month from the months_of_year enumeration - greg_month(months_of_year theMonth) : greg_month_rep(theMonth) {} + greg_month(month_enum theMonth) : greg_month_rep(theMonth) {} //! Construct from a short value greg_month(unsigned short theMonth) : greg_month_rep(theMonth) {} //! Convert the value back to a short diff --git a/include/boost/date_time/local_time_adjustor.hpp b/include/boost/date_time/local_time_adjustor.hpp index d49c332..b23f74d 100644 --- a/include/boost/date_time/local_time_adjustor.hpp +++ b/include/boost/date_time/local_time_adjustor.hpp @@ -168,11 +168,11 @@ namespace boost { * For example: * @code * //eastern timezone is utc-5 - typedef date_time::us_local_adjustor us_eastern; - typedef date_time::us_local_adjustor us_central; - typedef date_time::us_local_adjustor us_mountain; - typedef date_time::us_local_adjustor us_pacific; - typedef date_time::us_local_adjustor us_arizona; + typedef date_time::local_adjustor us_eastern; + typedef date_time::local_adjustor us_central; + typedef date_time::local_adjustor us_mountain; + typedef date_time::local_adjustor us_pacific; + typedef date_time::local_adjustor us_arizona; @endcode */ diff --git a/test/gregorian/testgenerators.cpp b/test/gregorian/testgenerators.cpp index 44cdcaa..65409b8 100644 --- a/test/gregorian/testgenerators.cpp +++ b/test/gregorian/testgenerators.cpp @@ -13,11 +13,18 @@ main() using namespace boost::gregorian; - partial_date pd(1,1); - date d = pd.get_date(2000); + partial_date pd1(1,Jan); + date d = pd1.get_date(2000); check("Partial date getdate", date(2000,1,1) == d); - d = pd.get_date(2001); + d = pd1.get_date(2001); check("Partial date getdate", date(2001,1,1) == d); + partial_date pd2(1,Feb); + check("Partial date operator==", pd1 == pd1); + check("Partial date operator==", !(pd1 == pd2)); + check("Partial date operator==", !(pd2 == pd1)); + check("Partial date operator<", !(pd1 < pd1)); + check("Partial date operator<", pd1 < pd2); + check("Partial date operator<", !(pd2 < pd1)); typedef boost::date_time::last_kday_of_month lastkday; diff --git a/test/posix_time/testdst_rules.cpp b/test/posix_time/testdst_rules.cpp index df11cf6..028d8d3 100644 --- a/test/posix_time/testdst_rules.cpp +++ b/test/posix_time/testdst_rules.cpp @@ -4,9 +4,30 @@ */ #include "boost/date_time/posix_time/posix_time.hpp" -#include "boost/date_time/dst_rules.hpp" +#include "boost/date_time/local_timezone_defs.hpp" #include "boost/date_time/testfrmwk.hpp" +// Define dst rule for Paraguay which is transitions forward on Oct 1 and +// back Mar 1 + +struct paraguay_dst_traits { + typedef boost::gregorian::date::day_type day_type; + typedef boost::gregorian::date::month_type month_type; + typedef boost::date_time::partial_date start_rule_functor; + typedef boost::date_time::partial_date end_rule_functor; + static day_type start_day() {return 1;} + static month_type start_month() {return boost::date_time::Oct;} + static day_type end_day() {return 1;} + static month_type end_month() {return boost::date_time::Mar;} + static int dst_start_offset_minutes() { return 120;} + static int dst_end_offset_minutes() { return 120; } + static int dst_shift_length_minutes() { return 60; } + +}; + + +// see http://www.timeanddate.com/time/aboutdst.html for some info +// also int main() { @@ -145,9 +166,240 @@ main() 60); check("check southern boundary-not", a10==boost::date_time::is_not_in_dst); + /******************** post release 1 -- new dst calc engine ********/ + + typedef boost::date_time::us_dst_trait us_dst_traits; + typedef boost::date_time::dst_calc_engine + us_dst_calc2; + + // us_dst_calc2 + check("dst start", us_dst_calc2::local_dst_start_day(2002) == dst_start); + check("dst end", us_dst_calc2::local_dst_end_day(2002) == dst_end); + // std::cout << us_dst_calc2::local_dst_end_day(2002) << std::endl; + check("dst boundary", us_dst_calc2::is_dst_boundary_day(dst_start)); + check("dst boundary", us_dst_calc2::is_dst_boundary_day(dst_end)); + + check("check if time is dst -- not", + us_dst_calc2::local_is_dst(t.date(), t.time_of_day())==boost::date_time::is_not_in_dst); + check("label on dst boundary invalid", + us_dst_calc2::local_is_dst(t3a.date(),t3a.time_of_day())==boost::date_time::invalid_time_label); + check("label on dst boundary invalid", + us_dst_calc2::local_is_dst(t3b.date(),t3b.time_of_day())==boost::date_time::invalid_time_label); + check("check if time is dst -- not", + us_dst_calc2::local_is_dst(t4.date(),t4.time_of_day())==boost::date_time::is_not_in_dst); + check("check if time is dst -- yes", + us_dst_calc2::local_is_dst(t5.date(),t5.time_of_day())==boost::date_time::is_in_dst); + + check("check if time is dst -- not", + us_dst_calc2::local_is_dst(t6.date(),t6.time_of_day())==boost::date_time::is_in_dst); + check("check if time is dst -- ambig", + us_dst_calc2::local_is_dst(t7.date(),t7.time_of_day())==boost::date_time::ambiguous); + check("check if time is dst -- ambig", + us_dst_calc2::local_is_dst(t8.date(),t8.time_of_day())==boost::date_time::ambiguous); + check("check if time is dst -- not", + us_dst_calc2::local_is_dst(t9.date(),t9.time_of_day())==boost::date_time::is_not_in_dst); + + + /******************** post release 1 -- new dst calc engine - eu dst ********/ + + + typedef boost::date_time::eu_dst_trait eu_dst_traits; + typedef boost::date_time::dst_calc_engine + eu_dst_calc; + date eu_dst_start(2002,Mar, 31); + date eu_dst_end(2002,Oct, 27); + ptime eu_invalid1(eu_dst_start, time_duration(2,0,0)); //invalid time label + ptime eu_invalid2(eu_dst_start, time_duration(2,59,59)); //invalid time label + ptime eu_notdst1(eu_dst_start, time_duration(1,59,59)); //not ds + ptime eu_isdst1(eu_dst_start, time_duration(3,0,0)); //always dst + ptime eu_isdst2(eu_dst_end, time_duration(1,59,59)); //is dst + ptime eu_amgbig1(eu_dst_end, time_duration(2,0,0)); //ambiguous + ptime eu_amgbig2(eu_dst_end, time_duration(2,59,59)); //ambiguous + ptime eu_notdst2(eu_dst_end, time_duration(3,0,0)); //always not dst + + check("eu dst start", eu_dst_calc::local_dst_start_day(2002) == eu_dst_start); + check("eu dst end", eu_dst_calc::local_dst_end_day(2002) == eu_dst_end); + check("eu dst boundary", eu_dst_calc::is_dst_boundary_day(eu_dst_start)); + check("eu dst boundary", eu_dst_calc::is_dst_boundary_day(eu_dst_end)); + // on forward shift boundaries + check("eu label on dst boundary invalid", + eu_dst_calc::local_is_dst(eu_invalid1.date(),eu_invalid1.time_of_day())==boost::date_time::invalid_time_label); + check("eu label on dst boundary invalid", + eu_dst_calc::local_is_dst(eu_invalid2.date(),eu_invalid2.time_of_day())==boost::date_time::invalid_time_label); + check("eu check if time is dst -- not", + eu_dst_calc::local_is_dst(eu_notdst1.date(),eu_notdst1.time_of_day())==boost::date_time::is_not_in_dst); + check("check if time is dst -- yes", + eu_dst_calc::local_is_dst(eu_isdst1.date(),eu_isdst1.time_of_day())==boost::date_time::is_in_dst); + //backward shift boundary + check("eu check if time is dst -- yes", + eu_dst_calc::local_is_dst(eu_isdst2.date(),eu_isdst2.time_of_day())==boost::date_time::is_in_dst); + check("eu check if time is dst -- ambig", + eu_dst_calc::local_is_dst(eu_amgbig1.date(),eu_amgbig1.time_of_day())==boost::date_time::ambiguous); + check("eu check if time is dst -- ambig", + eu_dst_calc::local_is_dst(eu_amgbig2.date(),eu_amgbig2.time_of_day())==boost::date_time::ambiguous); + check("eu check if time is dst -- not", + eu_dst_calc::local_is_dst(eu_notdst2.date(),eu_notdst2.time_of_day())==boost::date_time::is_not_in_dst); + +/******************** post release 1 -- new dst calc engine - gb dst ********/ + + + /* Several places in Great Britan use eu start and end rules for the + day, but different local conversion times (eg: forward change at 1:00 + am local and backward change at 2:00 am dst instead of 2:00am + forward and 3:00am back for the EU). + */ + + typedef boost::date_time::uk_dst_trait uk_dst_traits; + + typedef boost::date_time::dst_calc_engine uk_dst_calc; + + + date uk_dst_start(2002,Mar, 31); + date uk_dst_end(2002,Oct, 27); + ptime uk_invalid1(uk_dst_start, time_duration(1,0,0)); //invalid time label + ptime uk_invalid2(uk_dst_start, time_duration(1,59,59)); //invalid time label + ptime uk_notdst1(uk_dst_start, time_duration(0,59,59)); //not ds + ptime uk_isdst1(uk_dst_start, time_duration(2,0,0)); //always dst + ptime uk_isdst2(uk_dst_end, time_duration(0,59,59)); //is dst + ptime uk_amgbig1(uk_dst_end, time_duration(1,0,0)); //ambiguous + ptime uk_amgbig2(uk_dst_end, time_duration(1,59,59)); //ambiguous + ptime uk_notdst2(uk_dst_end, time_duration(3,0,0)); //always not dst + + check("uk dst start", uk_dst_calc::local_dst_start_day(2002) == uk_dst_start); + check("uk dst end", uk_dst_calc::local_dst_end_day(2002) == uk_dst_end); + check("uk dst boundary", uk_dst_calc::is_dst_boundary_day(uk_dst_start)); + check("uk dst boundary", uk_dst_calc::is_dst_boundary_day(uk_dst_end)); + // on forward shift boundaries + check("uk label on dst boundary invalid", + uk_dst_calc::local_is_dst(uk_invalid1.date(),uk_invalid1.time_of_day())==boost::date_time::invalid_time_label); + check("uk label on dst boundary invalid", + uk_dst_calc::local_is_dst(uk_invalid2.date(),uk_invalid2.time_of_day())==boost::date_time::invalid_time_label); + check("uk check if time is dst -- not", + uk_dst_calc::local_is_dst(uk_notdst1.date(),uk_notdst1.time_of_day())==boost::date_time::is_not_in_dst); + check("uk check if time is dst -- yes", + uk_dst_calc::local_is_dst(uk_isdst1.date(),uk_isdst1.time_of_day())==boost::date_time::is_in_dst); + //backward shift boundary + check("uk check if time is dst -- yes", + uk_dst_calc::local_is_dst(uk_isdst2.date(),uk_isdst2.time_of_day())==boost::date_time::is_in_dst); + check("uk check if time is dst -- ambig", + uk_dst_calc::local_is_dst(uk_amgbig1.date(),uk_amgbig1.time_of_day())==boost::date_time::ambiguous); + check("uk check if time is dst -- ambig", + uk_dst_calc::local_is_dst(uk_amgbig2.date(),uk_amgbig2.time_of_day())==boost::date_time::ambiguous); + check("uk check if time is dst -- not", + uk_dst_calc::local_is_dst(uk_notdst2.date(),uk_notdst2.time_of_day())==boost::date_time::is_not_in_dst); + + +// /******************** post release 1 -- new dst calc engine ********/ + +// //Define dst rule for Paraguay which is transitions forward on Oct 1 and back Mar 1 + + typedef boost::date_time::dst_calc_engine pg_dst_calc; + + { + + date pg_dst_start(2002,Oct, 1); + date pg_dst_end(2002,Mar, 1); + date pg_indst(2002,Dec, 1); + date pg_notdst(2002,Jul, 1); + ptime pg_invalid1(pg_dst_start, time_duration(2,0,0)); //invalid time label + ptime pg_invalid2(pg_dst_start, time_duration(2,59,59)); //invalid time label + ptime pg_notdst1(pg_dst_start, time_duration(1,59,59)); //not ds + ptime pg_isdst1(pg_dst_start, time_duration(3,0,0)); //always dst + ptime pg_isdst2(pg_dst_end, time_duration(0,59,59)); //is dst + ptime pg_amgbig1(pg_dst_end, time_duration(1,0,0)); //ambiguous + ptime pg_amgbig2(pg_dst_end, time_duration(1,59,59)); //ambiguous + ptime pg_notdst2(pg_dst_end, time_duration(2,0,0)); //always not dst + + check("pg dst start", pg_dst_calc::local_dst_start_day(2002) == pg_dst_start); + check("pg dst end", pg_dst_calc::local_dst_end_day(2002) == pg_dst_end); + check("pg dst boundary", pg_dst_calc::is_dst_boundary_day(pg_dst_start)); + check("pg dst boundary", pg_dst_calc::is_dst_boundary_day(pg_dst_end)); + // on forward shift boundaries + check("pg label on dst boundary invalid", + pg_dst_calc::local_is_dst(pg_invalid1.date(),pg_invalid1.time_of_day())==boost::date_time::invalid_time_label); + check("pg label on dst boundary invalid", + pg_dst_calc::local_is_dst(pg_invalid2.date(),pg_invalid2.time_of_day())==boost::date_time::invalid_time_label); + check("pg check if time is dst -- not", + pg_dst_calc::local_is_dst(pg_notdst1.date(),pg_notdst1.time_of_day())==boost::date_time::is_not_in_dst); + check("check if time is dst -- yes", + pg_dst_calc::local_is_dst(pg_isdst1.date(),pg_isdst1.time_of_day())==boost::date_time::is_in_dst); + //backward shift boundary + check("pg check if time is dst -- yes", + pg_dst_calc::local_is_dst(pg_isdst2.date(),pg_isdst2.time_of_day())==boost::date_time::is_in_dst); + check("pg check if time is dst -- ambig", + pg_dst_calc::local_is_dst(pg_amgbig1.date(),pg_amgbig1.time_of_day())==boost::date_time::ambiguous); + check("pg check if time is dst -- ambig", + pg_dst_calc::local_is_dst(pg_amgbig2.date(),pg_amgbig2.time_of_day())==boost::date_time::ambiguous); + check("pg check if time is dst -- not", + pg_dst_calc::local_is_dst(pg_notdst2.date(),pg_notdst2.time_of_day())==boost::date_time::is_not_in_dst); + // a couple not on the boudnary + check("pg check if time is dst -- yes", + pg_dst_calc::local_is_dst(pg_indst,time_duration(0,0,0))==boost::date_time::is_in_dst); + check("pg check if time is dst -- not", + pg_dst_calc::local_is_dst(pg_notdst,time_duration(0,0,0))==boost::date_time::is_not_in_dst); + + } + +// /******************** post release 1 -- new dst calc engine ********/ + +// //Define dst rule for Adelaide australia + + typedef boost::date_time::acst_dst_trait acst_dst_traits; + typedef boost::date_time::dst_calc_engine acst_dst_calc; + + { + + date acst_dst_start(2002,Oct, 27); + date acst_dst_end(2002,Mar, 31); + date acst_indst(2002,Dec, 1); + date acst_notdst(2002,Jul, 1); + ptime acst_invalid1(acst_dst_start, time_duration(2,0,0)); //invalid time label + ptime acst_invalid2(acst_dst_start, time_duration(2,59,59)); //invalid time label + ptime acst_notdst1(acst_dst_start, time_duration(1,59,59)); //not ds + ptime acst_isdst1(acst_dst_start, time_duration(3,0,0)); //always dst + ptime acst_isdst2(acst_dst_end, time_duration(0,59,59)); //is dst + ptime acst_amgbig1(acst_dst_end, time_duration(1,0,0)); //ambiguous + ptime acst_amgbig2(acst_dst_end, time_duration(1,59,59)); //ambiguous + ptime acst_notdst2(acst_dst_end, time_duration(2,0,0)); //always not dst + + std::cout << "acst dst_start: " << acst_dst_calc::local_dst_start_day(2002) + << std::endl; + check("acst dst start", acst_dst_calc::local_dst_start_day(2002) == acst_dst_start); + check("acst dst end", acst_dst_calc::local_dst_end_day(2002) == acst_dst_end); + check("acst dst boundary", acst_dst_calc::is_dst_boundary_day(acst_dst_start)); + check("acst dst boundary", acst_dst_calc::is_dst_boundary_day(acst_dst_end)); + // on forward shift boundaries + check("acst label on dst boundary invalid", + acst_dst_calc::local_is_dst(acst_invalid1.date(),acst_invalid1.time_of_day())==boost::date_time::invalid_time_label); + check("acst label on dst boundary invalid", + acst_dst_calc::local_is_dst(acst_invalid2.date(),acst_invalid2.time_of_day())==boost::date_time::invalid_time_label); + check("acst check if time is dst -- not", + acst_dst_calc::local_is_dst(acst_notdst1.date(),acst_notdst1.time_of_day())==boost::date_time::is_not_in_dst); + check("check if time is dst -- yes", + acst_dst_calc::local_is_dst(acst_isdst1.date(),acst_isdst1.time_of_day())==boost::date_time::is_in_dst); + //backward shift boundary + check("acst check if time is dst -- yes", + acst_dst_calc::local_is_dst(acst_isdst2.date(),acst_isdst2.time_of_day())==boost::date_time::is_in_dst); + check("acst check if time is dst -- ambig", + acst_dst_calc::local_is_dst(acst_amgbig1.date(),acst_amgbig1.time_of_day())==boost::date_time::ambiguous); + check("acst check if time is dst -- ambig", + acst_dst_calc::local_is_dst(acst_amgbig2.date(),acst_amgbig2.time_of_day())==boost::date_time::ambiguous); + check("acst check if time is dst -- not", + acst_dst_calc::local_is_dst(acst_notdst2.date(),acst_notdst2.time_of_day())==boost::date_time::is_not_in_dst); + // a couple not on the boudnary + check("acst check if time is dst -- yes", + acst_dst_calc::local_is_dst(acst_indst,time_duration(0,0,0))==boost::date_time::is_in_dst); + check("acst check if time is dst -- not", + acst_dst_calc::local_is_dst(acst_notdst,time_duration(0,0,0))==boost::date_time::is_not_in_dst); + ptime utc_t = ptime(acst_dst_start, hours(2)) - time_duration(16,30,0); + std::cout << "UTC date/time of Adelaide switch over: " << utc_t << std::endl; + + } + + return printTestStats(); - printTestStats(); - return 0; } /* diff --git a/test/posix_time/testlocal_adjustor.cpp b/test/posix_time/testlocal_adjustor.cpp index 0898adf..a827f2f 100644 --- a/test/posix_time/testlocal_adjustor.cpp +++ b/test/posix_time/testlocal_adjustor.cpp @@ -5,6 +5,7 @@ #include "boost/date_time/posix_time/posix_time.hpp" #include "boost/date_time/local_time_adjustor.hpp" +#include "boost/date_time/local_timezone_defs.hpp" #include "boost/date_time/testfrmwk.hpp" int @@ -125,6 +126,19 @@ main() check("check us_local_adjustor", t7c == t7a); + typedef boost::date_time::us_dst_trait us_dst_traits; + typedef boost::date_time::dst_calc_engine + us_dst_calc2; + + typedef boost::date_time::local_adjustor us_eastern3; + { + ptime t7a(date(2002,May,31), hours(17)); + ptime t7b = us_eastern3::local_to_utc(t7a); + ptime t7c = us_eastern3::utc_to_local(t7b); + //converted to local then back ot utc + check("check us_local_adjustor3", t7c == t7a); + } + // std::cout << to_simple_string(t7) << " in Arizona is " // << to_simple_string(t8) << " UTC time " // << std::endl;