1

DimensionDate2011,12,31 から 2032,1,1 までのすべての日付を含むというテーブルを生成しました。

ここで、各日付について、これら 2 つの日付の間の 1 か月の絶対範囲を知りたいと思います。

例えば ​​:

2012-01-01 は 1 か月の数字です

2012-02-01 は 2 番目の月です

2013-01-01 は 13 番目の月です

2013-02-01 は 14 番目の月です

2014-01-01 は 25 番目の月です

2014-02-01 は 26 番目の月です

等...

どうすればそれができますか?何か案が ?ご協力いただきありがとうございます

4

2 に答える 2

6

このようなもの?

require 'date'

def months_between_dates(date_1, date_2)
  diff_in_years  = (date_1.year-date_2.year)*12
  diff_in_months = date_1.month-date_2.month
  return (diff_in_years + diff_in_months).abs
end

start_date  = Date.new(2011,12,31)
test_date   = Date.new(2013,01,01)
test_date_2 = Date.new(2014,02,01)

p months_between_dates(start_date, test_date)   # => 13
p months_between_dates(start_date, test_date_2) # => 26

編集:

おまけとして、常に特定の日付と比較することがわかっている場合は、デフォルト値のバージョンがあります。ロジックは同じですが、読みやすいのではなく、短いだけです。

# Call by passing one or two dates:
def delta_months(x, y=Date.new(2011,12,31))
  ((x.year-y.year)*12+(x.month-y.month)).abs 
end

p delta_months(test_date)  # => 13

編集2:

ダックスが指摘したように、私の関数はいかなる形式の検証も提供しません。これを実装する方法は次のとおりです。

MIN_DATE, MAX_DATE = Date.new(2011,12,31), Date.new(2032,1,1)
date_range = MIN_DATE..MAX_DATE
test_date  = Date.new(2064,1,1)

raise "Date out of range, must be between #{MIN_DATE} and #{MAX_DATE}." unless date_range.cover? test_date # => Date out of range, must be between 2011-12-31 and 2032-01-01. (RuntimeError)
delta_months(test_date)  # Never called unless good date is provided.
于 2013-10-14T11:54:15.760 に答える
1

Hirolauの答えは良いですが、これはより簡単に/エラー防止できると思います。開始時間は絶対的なので、メソッドの引数に含める必要はありません。終了時間に対してもテストできます。

def dimensional_date_range(now)
  range = (now.year - 2012)*12 + (now.month)
  if range <= 240 
    range
  else
    "you're out of this dimension, man!"
  end
end

テスト済み:

$ date =  Date.new(2014,02,01)
$ date2 = Date.new(2050,01,01)
$ dimensional_date_range(date)
 => 26
$ dimensional_date_range(date2)
 => "you're out of this dimension, man!"
于 2013-10-14T12:28:54.140 に答える