Calculate last day of month

This is probably an easy one for somebody, but I couldn't figure it out
using the Date class in the documentation.

require 'date'

d = Date.new(2006, 9,16)

How do I return the date for the last day of this month (September in
this example)?

Thank you for your help!

-Hunter

···

--
Posted via http://www.ruby-forum.com/.

Hunter Walker wrote:

This is probably an easy one for somebody, but I couldn't figure it out
using the Date class in the documentation.

How do I return the date for the last day of this month (September in
this example)?

Easy: Construct a date for the first day of the following month, then
subtract one day and read the resulting components.

Hard: construct a date for the first day of the target month, then add days
unitil the month number changes. Then go back one.

I think I know which option you'll choose. :slight_smile:

···

--
Paul Lutus
http://www.arachnoid.com

How do I return the date for the last day of this month (September in
this example)?

Looking for an alternate way: could this be a step in the right
direction?
(See http://chronic.rubyforge.org/\)

irb(main):001:0> require 'chronic'
irb(main):011:0> Chronic.parse('last day of this month')
=> nil
Well... this was close.
:slight_smile:

Date.new((Date.today>>1).year,(Date.today>>1).month,1)-1)

-Thomas

···

On 21/09/06, Hunter Walker <walkerhunter@gmail.com> wrote:

How do I return the date for the last day of this month (September in
this example)?

Hunter Walker wrote:

This is probably an easy one for somebody, but I couldn't figure it out
using the Date class in the documentation.

require 'date'

d = Date.new(2006, 9,16)

How do I return the date for the last day of this month (September in
this example)?

Thank you for your help!

-Hunter

Date.new(2006, 9,-1)

-1 means count backwards in this context. more info at
http://www.ruby-doc.org/core/classes/Date.html#M001193

···

--
Posted via http://www.ruby-forum.com/\.

class Date
  def self.last_day_of_the_month(yyyy, mm)
    new(yyyy, mm).next_month - 1
  end
end

···

--
Posted via http://www.ruby-forum.com/.

except you have to handle december specially - else you'll end up with the
with the wrong year.

easiest is probably:

harp:~ > cat a.rb
require 'date'

class Date
   def self.last_day_of_the_month yyyy, mm
     d = new yyyy, mm
     d += 42 # warp into the next month
     new(d.year, d.month) - 1 # back off one day from first of that month
   end
end

puts Date.last_day_of_the_month(2006, 9)
puts Date.last_day_of_the_month(2006, 12)
puts Date.last_day_of_the_month(2007, 2)

harp:~ > ruby a.rb
2006-09-30
2006-12-31
2007-02-28

-a

···

On Fri, 22 Sep 2006, Paul Lutus wrote:

Hunter Walker wrote:

This is probably an easy one for somebody, but I couldn't figure it out
using the Date class in the documentation.

How do I return the date for the last day of this month (September in this
example)?

Easy: Construct a date for the first day of the following month, then
subtract one day and read the resulting components.

Hard: construct a date for the first day of the target month, then add days
unitil the month number changes. Then go back one.

I think I know which option you'll choose. :slight_smile:

--
in order to be effective truth must penetrate like an arrow - and that is
likely to hurt. -- wei wu wei

It's easier than that.

class Date
  def self.last_day_of_the_month(yyyy, mm)
    new(yyyy, mm, -1)
  end
end

--Greg

···

On Wed, Jul 16, 2008 at 11:41:32AM +0900, Platoon Tb wrote:

class Date
  def self.last_day_of_the_month(yyyy, mm)
    new(yyyy, mm).next_month - 1
  end
end

Very cool! That worked! Thank you!

-Hunter

···

--
Posted via http://www.ruby-forum.com/.

     d += 42 # warp into the next month

You need to add a month, not a fixed number of days, since you can't predict
how many days are in the next month:

irb(main):033:0> d = Date.new 2006, 1, 31
=> #<Date: 4907533/2,0,2299161>
irb(main):034:0> (d >> 1).to_s
=> "2006-02-28"

irb(main):039:0> d = Date.new 1996, 1, 31
=> #<Date: 4900227/2,0,2299161>
irb(main):040:0> (d >> 1).to_s
=> "1996-02-29"

- James Moore

Ok, I know that I am going to be smacked for this, but we DO know how
many days are in each month. Why not just have one for february with
considerations for leap year, and lists for those with 30 and 31 days,
or possibly 30 days and everything else has 31. It is nothing more than
a lookup.

Is that too easy or too non Ruby-ish?

···

--
Posted via http://www.ruby-forum.com/.

Gregory Seidman wrote:

It's easier than that.

class Date
  def self.last_day_of_the_month(yyyy, mm)
    new(yyyy, mm, -1)
  end
end

Why override Date at all when we've got
ActiveSupport::CoreExtensions::date::Calculations and can just use
'end_of_month'?

Yeah that was my first thought too, but notice he is constructing a
new date at the beginning of the month. I am guessing he picked 42,
over 32 as it is just much better number.

pth

···

On 9/21/06, James Moore <banshee@banshee.com> wrote:

> d += 42 # warp into the next month

You need to add a month, not a fixed number of days, since you can't predict
how many days are in the next month:

irb(main):033:0> d = Date.new 2006, 1, 31
=> #<Date: 4907533/2,0,2299161>
irb(main):034:0> (d >> 1).to_s
=> "2006-02-28"

irb(main):039:0> d = Date.new 1996, 1, 31
=> #<Date: 4900227/2,0,2299161>
irb(main):040:0> (d >> 1).to_s
=> "1996-02-29"

- James Moore

Because this is the ruby list, not the rubyonrails list.

--Greg

···

On Wed, Jul 16, 2008 at 10:44:35PM +0900, Bill Walton wrote:

Gregory Seidman wrote:

> It's easier than that.
>
> class Date
> def self.last_day_of_the_month(yyyy, mm)
> new(yyyy, mm, -1)
> end
> end

Why override Date at all when we've got
ActiveSupport::CoreExtensions::date::Calculations and can just use
'end_of_month'?

exactly :wink:

the point is that it always lands into the next month.

-a

···

On Fri, 22 Sep 2006, Patrick Hurley wrote:

Yeah that was my first thought too, but notice he is constructing a
new date at the beginning of the month. I am guessing he picked 42,
over 32 as it is just much better number.

--
in order to be effective truth must penetrate like an arrow - and that is
likely to hurt. -- wei wu wei

Gregory Seidman wrote:

···

On Wed, Jul 16, 2008 at 10:44:35PM +0900, Bill Walton wrote:
>
> Why override Date at all when we've got
> ActiveSupport::CoreExtensions::date::Calculations and can just use
> 'end_of_month'?

Because this is the ruby list, not the rubyonrails list.

--Greg

Oops :wink: Should have checked the header. My bad.

Best regards,
Bill

Or the month after that - depending on where you start. :slight_smile:

  robert

···

ara.t.howard@noaa.gov wrote:

On Fri, 22 Sep 2006, Patrick Hurley wrote:

Yeah that was my first thought too, but notice he is constructing a
new date at the beginning of the month. I am guessing he picked 42,
over 32 as it is just much better number.

exactly :wink:

the point is that it always lands into the next month.

sure - but it always starts on the first day of the month:

require 'date'

class Date
   def self.last_day_of_the_month yyyy, mm
     d = new yyyy, mm # no day means the first one
     d += 42 # always the next month
     new(d.year, d.month) - 1
   end
end

puts Date.last_day_of_the_month(2006, 9)
puts Date.last_day_of_the_month(2006, 12)
puts Date.last_day_of_the_month(2007, 2)

cheers.

-a

···

On Fri, 22 Sep 2006, Robert Klemme wrote:

ara.t.howard@noaa.gov wrote:

On Fri, 22 Sep 2006, Patrick Hurley wrote:

Yeah that was my first thought too, but notice he is constructing a
new date at the beginning of the month. I am guessing he picked 42,
over 32 as it is just much better number.

exactly :wink:

the point is that it always lands into the next month.

Or the month after that - depending on where you start. :slight_smile:

--
in order to be effective truth must penetrate like an arrow - and that is
likely to hurt. -- wei wu wei

Yes, of course. I didn't want to insunuate you code would not do what you claimed it to do. It was merely a silly remark, probably stirred up by this strange number that I haven't seen in a while. I am sorry.

Kind regards

    robert

···

ara.t.howard@noaa.gov wrote:

On Fri, 22 Sep 2006, Robert Klemme wrote:

ara.t.howard@noaa.gov wrote:

On Fri, 22 Sep 2006, Patrick Hurley wrote:

Yeah that was my first thought too, but notice he is constructing a
new date at the beginning of the month. I am guessing he picked 42,
over 32 as it is just much better number.

exactly :wink:

the point is that it always lands into the next month.

Or the month after that - depending on where you start. :slight_smile:

sure - but it always starts on the first day of the month:

I've had this problem often enough to make a gem of my solution:

require 'expanded_date'

d = Date.new => 2006-09-22
d.end_of_month => 2006-09-30
d.end_of_next_month => 2006-10-31

The gems is in production use and will continue to be maintained.

Any feedback would be welcome.

Rdoc: http://backofficegems.rubyforge.org/expanded_date/doc/

···

--
Jon Egil Strand
Phone: +47 98232340
jes@luretanker.no