Add a month to a Date object

Howdy all,

This may be the dumbest question in the world, but how can you "add
one month" to a Date object? I can't just add 30 days, because months
have varying lengths.

Any help would be much appreciated...

Thanks!

-Neal

if you convert it to time you can use 'advance', and then convert it
back to a date. For example:

date_object.to_time.advance(1.month).to_date

http://api.rubyonrails.com/classes/ActiveSupport/CoreExtensions/DateTime/Calculations.html#M000714

oops, wrong syntax. Should be:

date_object.to_time.advance(:months => 1).to_date

If you have a Date object (i.e, not a Time object), then use >> and << to go forward and backward by month. If you have a Time (since you're in Rails), you can use months_ago or months_since.

2.months_since(Time.now)

Compare that to (2.months).since(Time.now) particularly in the last few days of the month.

-Rob

Rob Biedenharn http://agileconsultingllc.com
Rob@AgileConsultingLLC.com

Note:

IMO the best way to do this is trough << and >>. But watch out in
iterating blocks, like while, for & etc. You might end up in the wrong
day if you keep doing something like date >> 1

Example:

date = '2007-12-31'.to_date
while date <= '2008-3-31'.to_date
  puts date
  date >> 1
end

This is going to be your output:
(the formatting of the date is going to be different, this is just an
example)

Dec 31, 2007
Jan 31, 2008
Feb 29, 2008
Mar 29, 2008 (note that your date has day = 29)

If instead you do something like:

date = '2007-12-31'.to_date
c = 0
while date <= '2008-3-31'.to_date
  puts date
  c = c + 1 #this is the same as c += 1
  date = date >> c #this is the same as date =>> c
end
(This code could be shorter, but would be harder to understand)

This is going to be your output:

Dec 31, 2007
Jan 31, 2008
Feb 29, 2008
Mar 31, 2008

The difference is that in the first approach, you always do date >> 1,
several times. In the second, you do date >> 1 the first time, date >>
2 the second, and so on.

I had a brain fart. The second code is WRONG and wont work as
expected. This should work.

date = '2007-12-31'.to_date
c = 0
while date >> c <= '2008-3-31'.to_date
  puts date >> c
  c = c + 1 #this is the same as c += 1
end

This is going to be your output:

Dec 31, 2007
Jan 31, 2008
Feb 29, 2008
Mar 31, 2008