在片刻范围内寻找闰年

时间:2017-06-16 05:43:09

标签: javascript momentjs

我尝试使用moment.js和moment-range来确定给定的日期范围是否包含闰年和闰日(2月29日)。

// Really checks for leap day, not only leap year.
function dateRangeContainsLeapYear(dateRange) {
  return dateRange.toArray('years').some((year) => {
    return year.isLeapYear() && dateRange.contains(moment([year.year(), 1, 29]));
  });
}

// Scenario 1
var start = moment('2015-07-01', 'YYYY-MM-DD');
var end = moment('2016-06-30', 'YYYY-MM-DD');

var dateRange = moment().range(start, end);
var dateRangeLength = dateRange.toArray('days').length; // 366

var output = dateRangeContainsLeapYear(dateRange);
console.log(output); // false

// Scenario 2
var start = moment('2015-07-01', 'YYYY-MM-DD');
var end = moment('2016-07-01', 'YYYY-MM-DD');

var dateRange = moment().range(start, end);
var dateRangeLength = dateRange.toArray('days').length; // 367

var output = dateRangeContainsLeapYear(dateRange);
console.log(output); // true

// Scenario 3
var start = moment('2016-01-01', 'YYYY-MM-DD');
var end = moment('2016-06-30', 'YYYY-MM-DD');

var dateRange = moment().range(start, end);
var dateRangeLength = dateRange.toArray('days').length; // 182

var output = dateRangeContainsLeapYear(dateRange);
console.log(output); // true

// Scenario 4
var start = moment('2015-07-01', 'YYYY-MM-DD');
var end = moment('2017-06-30', 'YYYY-MM-DD');

var dateRange = moment().range(start, end);
var dateRangeLength = dateRange.toArray('days').length; // 731

var output = dateRangeContainsLeapYear(dateRange);
console.log(output); // true

场景1返回false,因为dateRange.toArray('years')仅包含一个元素,即仅包含2015年。

解决这个问题的最佳方法是什么?

JSFiddle:https://jsfiddle.net/wwwescape/es931aa5/

1 个答案:

答案 0 :(得分:0)

你是对的,因为在片刻范围内没有简单的方法可以做到这一点。维护人员很乐意接受PR来解决这样的问题,其中可以将标志添加到range.by()方法以允许包含非整年/月/日。

我找到了一个相当优雅的解决方案,使用一个简单的循环来解决您的问题:

function dateRangeContainsLeapYear(dateRange) {
  for (var year = dateRange.start.year(); year <= dateRange.end.year(); year++) {
    var date = moment(year + '-02-29');
    if (date.isLeapYear() && dateRange.contains(date)) return true;
  }
  return false;
}

PS。确保更新您的时刻范围!转换为数组与API中的示例不同。