tzrule.sa


Generated by gen_html_sa_files from ICSI. Contact gomes@icsi.berkeley.edu for details
 
------------------------->  GNU Sather - sourcefile  <-------------------------
-- Copyright (C) 2000 by K Hopper, University of Waikato, New Zealand        --
-- This file is part of the GNU Sather library. It is free software; you may --
-- redistribute  and/or modify it under the terms of the GNU Library General --
-- Public  License (LGPL)  as published  by the  Free  Software  Foundation; --
-- either version 2 of the license, or (at your option) any later version.   --
-- This  library  is distributed  in the  hope that it will  be  useful, but --
-- WITHOUT ANY WARRANTY without even the implied warranty of MERCHANTABILITY --
-- or FITNESS FOR A PARTICULAR PURPOSE. See Doc/LGPL for more details.       --
-- The license text is also available from:  Free Software Foundation, Inc., --
-- 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA                     --
-------------->  Please email comments to <bug-sather@gnu.org>  <--------------


immutable class DATE_FORMS < $ENUMS{DATE_FORMS}

immutable class DATE_FORMS < $ENUMS{DATE_FORMS} is --This is an enumeration class which describes the different forms of -- date as specified in ISO/IEC 14652. -- The mandatory string names are - <blank>, "J", "M" -- Version 1.0 Feb 98. Copright K Hopper, U of Waikato -- Development History -- ------------------- -- Date Who By Detail -- ---- ------ ------ -- 25 Feb 98 kh Original include ENUM{DATE_FORMS} ; private const val_count : CARD := 3 ; -- The next routines provide the enumeration itself for a selection -- of the official registry encodings. Zero_Based : SAME is return enum(1) end ; Julian : SAME is return enum(2) end ; Gregorian : SAME is return enum(3) end ; end ; -- DATE_FORMS

immutable class TZ_RULE_ELEM < $STR, $BINARY

immutable class TZ_RULE_ELEM < $STR, $BINARY is -- This class is the descriptor of a time when the change from summer -- to standard time (or vice-versa) takes place. -- -- The model uses a two component 'date' giving either the day in week, -- week in month and month in year OR if week in month is zero then -- the day is considered to be the day in month, rather than day in week. -- Version 1.0 Feb 98. Copyright K Hopper, U of Waikato -- Development History -- ------------------- -- Date Who By Detail -- ---- ------ ------ -- 24 Feb 98 kh Original using ISO/IEC 14652 spec. include BINARY ; private attr day_number : CARD ; private attr week_number : CARD ; private attr month : CARD ; private attr time : TIMES ; create(day : CARD,week : CARD,mth : CARD,clock : TIMES) : SAME pre ((day > 0) and (day <= 7)) and ((week > 0) and (week <= 5)) and ((mth > 0) and (mth <= 12)) post ~void(result) is -- This creation routine makes the form of rule given as a particular -- day in a particular week of the given month. return day_number(day).week_number(week).month(mth).time(clock) end ; create(days : CARD,one_based : CARD,clock : TIMES) : SAME pre ((days > 0) and (days <= 365) and (one_based = 1)) or ((days > 0) and (days <= 366) and (one_based = 0)) post ~void(result) is -- This creation routine makes the form of rule given as a particular -- day in the year. If one_based is one then the form is based on the Julian -- year from 1 to 365 and it is not possible to refer to February 29th! return day_number(days).week_number(one_based).month(0).time(clock) end ; build(cursor : BIN_CURSOR) : SAME pre (cursor.remaining >= ((3 * CARD::zero.binstr.size) + TIMES::null.binstr.size)) post ~void(result) -- and it represents a rule! is --This creation routine creates a rule using the given string cursor. me : SAME ; me := me.day_number(HEXTET::build(cursor).card) ; me := me.week_number(cursor.get_item.card) ; me := me.month(cursor.get_item.card) ; me := me.time(TIMES::build(cursor)) ; return me end ; binstr : BINSTR pre ~void(self) post result.size > 0 is --This routine creates a storage representation of this rule element. return BINSTR::create + HEXTET::create(day_number) + OCTET::create(week_number) + OCTET::create(month) + time.binstr end ; time(year : CARD) : TIME_STAMP pre ~void(self) post ~void(result) is --This routine returns the full time as a local clock time at which -- the change corresponding to this rule element would/will take place in -- the given year. if month = 0 then -- a Julian rule if week_number = 1 then -- no leap day! if DATES::is_leap_year(year) then loc_day : CARD := day_number ; if day_number = 60 then loc_day := loc_day + 1 end ; return TIME_STAMP::create(DATES::create(loc_day,month,year),time) end else return TIME_STAMP::create(DATES::create(day_number + 1, month,year),time) end else -- work out day in month! loc_date : DATES := DATES::create(1,month,year) ; loc_day : CARD := loc_date.day_of_week ; day_in_month : CARD := day_number ; if day_in_month < loc_day then day_in_month := day_in_month + DATES::Days_in_Week end ; return TIME_STAMP::create(DATES::create((day_in_month - loc_day + 1), month,year),time) end end ; str(lib : LIBCHARS) : STR pre ~void(self) and ~void(lib) post result.size > 0 is --This routine converts the rule element to a textual representation -- which would be acceptable to a standard locale parser reading routine -- using the given repertoire and encoding. res : STR := STR::create ; if month = 0 then if week_number = 0 then res := res + day_number.str else res := res + DATE_FORMS::Julian.str(lib) + day_number.str(lib) end else res := res + DATE_FORMS::Gregorian.str(lib) + month.str(lib) + lib.Colon.char + week_number.str(lib) + lib.Colon.char + day_number.str(lib) end ; return res + lib.Solidus.char + time.str(lib) end ; str : STR pre ~void(self) post result.size > 0 is --This routine converts the rule element to a textual representation -- which would be acceptable to a standard locale parser reading routine. return str(LIBCHARS::default) end ; end ; -- TZ_RULE_ELEM

class TZONE_RULE < $BINARY

class TZONE_RULE < $BINARY is -- This class is the descriptor to be used when calculating local time -- from UTC and vice-versa. -- Version 1.0 Feb 98. Copyright K Hopper, U of Waikato -- Development History -- ------------------- -- Date Who By Detail -- ---- ------ ------ -- 23 Feb 98 kh Original using ISO/IEC 14652 spec. include BINARY ; private attr valid_range : RANGE ; private attr start : TZ_RULE_ELEM ; private attr stop : TZ_RULE_ELEM ; build(cursor : BIN_CURSOR) : SAME pre ~void(cursor) and ~cursor.is_done post ~void(result) or (cursor.index = initial(cursor.index)) is --This routine creates a new object from the contents of the binary -- string indicated. res : SAME := new ; start_index : CARD := cursor.index ; res.valid_range := RANGE::build(cursor) ; if cursor.is_done then cursor.set_index(start_index) ; return void end ; res.start := TZ_RULE_ELEM::build(cursor) ; if cursor.is_done then cursor.set_index(start_index) ; return void end ; res.stop := TZ_RULE_ELEM::build(cursor) ; if void(res.stop) then cursor.set_index(start_index) ; return void end ; return res end ; create(from : CARD,to : CARD) : SAME pre (from < to) -- may not be an empty range! post void(result.start) and void(result.stop) is -- This creation routine is provided for use by the program reading -- source text to create this object. me : SAME := new ; me.valid_range := RANGE::create(from, to) ; return me end ; create(from : CARD,to : CARD,start_rule : TZ_RULE_ELEM,stop_rule : TZ_RULE_ELEM) : SAME pre (from < to) and ~void(start_rule) and ~void(stop_rule) post ~void(result) is --This creation routine is provided for use by the program reading -- source text to create this object. me : SAME := create(from,to) ; me.start := start_rule ; me.stop := stop_rule ; return me end ; binstr : BINSTR pre ~void(self) post result.size > 0 is --This routine produces a binary string form representation of self. return valid_range.binstr + start.binstr + stop.binstr end ; applies(stamp : TIME_STAMP) : BOOL is --This predicate returns true if and only if the given time stamp is -- valid - within the range of years for this rule. return valid_range.contains(stamp.date.year) end ; is_summer(stamp : TIME_STAMP) : BOOL is --This predicate returns true if and only if the given time stamp is -- in the period of summer time as defined by this rule. yr : CARD := stamp.date.year ; res : BOOL ; if start.time(yr) < stop.time(yr) then -- northern hemisphere res := (start.time(yr) <= stamp) and (stop.time(yr) >= stamp) else -- southern hemisphere res := (stamp >= start.time(yr)) or (stamp <= stop.time(yr)) end ; return res end ; end ; -- TZONE_RULE