C
Colin Bartlett
Extending the original poster's question, as people here are aware
working in complete months in Gregorian calendars can be tricky. For
example, if you are trying to generate a series of dates at intervals
of an integer number of months (years are just 12 months) then - as
far as I'm aware - there's no "standard" way of doing it in Ruby, or
in many other computer languages for that matter. (I'd be delighted to
be contradicted: this also applies to anything else I've got wrong in
the following post.)
The Date method >> doesn't do it if the day of the month is greater than 28:
require 'date'
dt = Date.new( 2000, 1, 31 ) # 2000-01-31
dt = dt >> 1 # 2000-02-29; which is correct
dt = dt >> 1 # 2000-03-29; what is wanted is 2000-03-31
dt = dt >> 1 # 2000-04-29; what is wanted is 2000-04-30
(Of course, you can use dt >> 1; dt >> 2; dt >> 3; etc, but it's not elegant.)
Also, date2 - date will give the number of days, but as far as I am
aware there isn't a "standard" Ruby way of calculating periods between
two dates in terms of, for example, complete months. (Or complete 12
months, the original poster's problem.)
If there isn't anything "standard" out there which does this sort of
thing, I'd be more than happy to collaborate on something if people
would find it useful. Or if there are one or more "projects" out there
which work, or are close to working, I'd be happy to collaborate on
something which could become "standard". Or indeed in porting
something from another language.
I have done a lot of this type of working with Gregorian dates in
various computer languages, but my Ruby experience is very limited,
and I'm not a programmer. (Even though I've been reading this list
since 2003.) Also, I sometimes feel that programming is too English
and Western oriented, so I'd be interested (as far as is reasonably
practical) in making things more general than just the Gregorian
calendar after the date(s) that the Julian calendar was corrected.
I wrote some code some time ago: the proper names can be decided on
later, but I have in mind adding methods to Date
dt.to( dt2 ), dt2.from( dt )
both of which would return an instance of a Date_period class, which
would hold the number of days from dt to dt2, and also the number of
complete months and the number of days following the complete months.
(And the dates themselves - or rather their object references - for
various reasons, which might or might not be a good idea.) Date_period
would have methods to return days, complete years, years and days,
months and days, etc.
For a series of dates the idea is to sub-class or modify Date to have
an (optional?) instance variable @anniversary_day, which is needed to
be able to retain the "true" anniversary day as well as the day in the
month in the date instance. Or at least to add a Date method
step_with_anniversary, which would have an option for the anniversary
day to be 29, 30 or 31 even if the start date is 28 of February.
Depending on whether it's a good idea or not, + and - (and maybe <<
and >>) in Date (or the subclass) could be adapted to also work with
instances of Date_period, or new methods could be added to Date (or
the subclass).
There are some tricky problems to be solved, and this post is long
enough already, but I'd be more happy to correspond off list
(including sending copies of the code I have), and then report back.
working in complete months in Gregorian calendars can be tricky. For
example, if you are trying to generate a series of dates at intervals
of an integer number of months (years are just 12 months) then - as
far as I'm aware - there's no "standard" way of doing it in Ruby, or
in many other computer languages for that matter. (I'd be delighted to
be contradicted: this also applies to anything else I've got wrong in
the following post.)
The Date method >> doesn't do it if the day of the month is greater than 28:
require 'date'
dt = Date.new( 2000, 1, 31 ) # 2000-01-31
dt = dt >> 1 # 2000-02-29; which is correct
dt = dt >> 1 # 2000-03-29; what is wanted is 2000-03-31
dt = dt >> 1 # 2000-04-29; what is wanted is 2000-04-30
(Of course, you can use dt >> 1; dt >> 2; dt >> 3; etc, but it's not elegant.)
Also, date2 - date will give the number of days, but as far as I am
aware there isn't a "standard" Ruby way of calculating periods between
two dates in terms of, for example, complete months. (Or complete 12
months, the original poster's problem.)
If there isn't anything "standard" out there which does this sort of
thing, I'd be more than happy to collaborate on something if people
would find it useful. Or if there are one or more "projects" out there
which work, or are close to working, I'd be happy to collaborate on
something which could become "standard". Or indeed in porting
something from another language.
I have done a lot of this type of working with Gregorian dates in
various computer languages, but my Ruby experience is very limited,
and I'm not a programmer. (Even though I've been reading this list
since 2003.) Also, I sometimes feel that programming is too English
and Western oriented, so I'd be interested (as far as is reasonably
practical) in making things more general than just the Gregorian
calendar after the date(s) that the Julian calendar was corrected.
I wrote some code some time ago: the proper names can be decided on
later, but I have in mind adding methods to Date
dt.to( dt2 ), dt2.from( dt )
both of which would return an instance of a Date_period class, which
would hold the number of days from dt to dt2, and also the number of
complete months and the number of days following the complete months.
(And the dates themselves - or rather their object references - for
various reasons, which might or might not be a good idea.) Date_period
would have methods to return days, complete years, years and days,
months and days, etc.
For a series of dates the idea is to sub-class or modify Date to have
an (optional?) instance variable @anniversary_day, which is needed to
be able to retain the "true" anniversary day as well as the day in the
month in the date instance. Or at least to add a Date method
step_with_anniversary, which would have an option for the anniversary
day to be 29, 30 or 31 even if the start date is 28 of February.
Depending on whether it's a good idea or not, + and - (and maybe <<
and >>) in Date (or the subclass) could be adapted to also work with
instances of Date_period, or new methods could be added to Date (or
the subclass).
There are some tricky problems to be solved, and this post is long
enough already, but I'd be more happy to correspond off list
(including sending copies of the code I have), and then report back.