www.francisfish.com

Click Bookshop to see my novels. Buddhist, father of 2, Ruby on Rails programmer for money, and fiction writer.








Latest Articles:

Archive

Tag Cloud:

Stats:

  • Entries = 358
  • Notes = 35

General Links

    follow me on Twitter

    Getting the number of months between two dates in Ruby/Rails - updated

    Published: 12:04 PM GMT, Wednesday, 2 April 2008

    Here lies the one that works, not the old one I posted ages ago. It also uses dates instead of timestamp differences and should therefore not break if you ask it to go before the Epoch (some time in 1970 I think):

    Also see Adrien's comment left here (he's much cleverer than me!) - it's really trivial:

    s is the start date and e is the end date (s is lower than e)

    (e.month - s.month) + 12 * (e.year - s.year)

    See!

    module DateUtils
    
      class << self
        def months_between( date1=Time.now, date2=Time.now )
    
          date1 ||= Time.now
          date2 ||= Time.now
    
          if date1 > date2
            recent_date = date1.to_date
    
            past_date = date2.to_date
          else
            recent_date = date2.to_date
    
            past_date = date1.to_date
          end
          years_diff = recent_date.year - past_date.year
    
          months_diff = recent_date.month - past_date.month
          if months_diff < 0
    
            months_diff = 12 + months_diff
            years_diff -= 1
    
          end
          years_diff*12 + months_diff
        end
    
      end
    
    end
    

    Comments (3)

    Thanks for the post and the subsequent comments. I have actually gone with Adrien's comment.

    Thanks Adrien.

    left by satya . Monday, 28 December 2009 4:43 PM

    Hi thanks for this useful post. I've copied your idea for a DateUtils module and put it in the lib of my rails app.

    Thought you might like to know that it can be squished into a two-liner making heavy use of parallel assignment...

    def months_between(date1=Date.today, date2=Date.today)

    (date1 > date2) ? (recent_date, past_date = date1, date2) : (recent_date, past_date = date2, date1)

    (recent_date.year - past_date.year) * 12 + (recent_date.month - past_date.month)

    end

    I don't think it loses too much readability...

    left by Henry . Wednesday, 18 June 2008 6:25 PM

    I've done this like that :

    s is the start date and e is the end date (s is lower than e)

    (e.month - s.month) + 12 * (e.year - s.year)

    left by Adrien . Tuesday, 15 April 2008 7:31 PM
    Add Comment