Обнаружение «недопустимой даты» экземпляра Date в JavaScript - PullRequest
1284 голосов
/ 30 августа 2009

Я бы хотел сказать разницу между действительными и недействительными объектами даты в JS, но не мог понять, как:

var d = new Date("foo");
console.log(d.toString()); // shows 'Invalid Date'
console.log(typeof d); // shows 'object'
console.log(d instanceof Date); // shows 'true'

Есть идеи по написанию функции isValidDate?

  • Пепел рекомендуется Date.parse для разбора строк даты, что дает авторитетный способ проверить, является ли строка даты действительной.
  • Что бы я предпочел, если это возможно, это чтобы мой API принимал экземпляр Date и мог проверить / подтвердить, действителен ли он или нет. Решение Borgar делает это, но мне нужно протестировать его в разных браузерах. Мне также интересно, есть ли более элегантный способ.
  • Эш заставил меня задуматься о том, чтобы мой API вообще не принимал Date экземпляров, это будет проще всего проверить.
  • Боргар предложил проверить экземпляр Date, а затем проверить значение времени Date. Если дата недействительна, значение времени равно NaN. Я проверил с ECMA-262 , и это поведение в стандарте, что именно то, что я ищу.

Ответы [ 40 ]

3 голосов
/ 25 июля 2014

Я объединил лучшие результаты производительности, которые я нашел вокруг этой проверки, если данный объект:

Результат следующий:

function isValidDate(input) {
  if(!(input && input.getTimezoneOffset && input.setUTCFullYear))
    return false;

  var time = input.getTime();
  return time === time;
};
2 голосов
/ 18 июня 2014

Выбранный ответ отличный, и я тоже им пользуюсь. Однако, если вы ищете способ проверки ввода даты пользователем, вы должны знать, что объект Date очень настойчив в том, чтобы превратить то, что может показаться недопустимым аргументом конструкции, в допустимые аргументы. Следующий код модульного теста иллюстрирует точку:

QUnit.test( "valid date test", function( assert ) {
  //The following are counter-examples showing how the Date object will 
  //wrangle several 'bad' dates into a valid date anyway
  assert.equal(isValidDate(new Date(1980, 12, 15)), true);
  d = new Date();
  d.setFullYear(1980);
  d.setMonth(1);
  d.setDate(33);
  assert.equal(isValidDate(d), true);
  assert.equal(isValidDate(new Date(1980, 100, 150)), true);
  //If you go to this exterme, then the checker will fail
  assert.equal(isValidDate(new Date("This is junk")), false);
  //This is a valid date string
  assert.equal(isValidDate(new Date("November 17, 1989")), true);
  //but is this?
  assert.equal(isValidDate(new Date("November 35, 1989")), false);  
  //Ha!  It's not.  So, the secret to working with this version of 
  //isValidDate is to pass in dates as text strings... Hooboy
  //alert(d.toString());
});
2 голосов
/ 23 ноября 2013

вы можете конвертировать вашу дату и время в миллисекунды getTime ()

this getTime() Метод return Не число NaN, если оно недействительно

if(!isNaN(new Date("2012/25/255").getTime()))
  return 'valid date time';
  return 'Not a valid date time';
2 голосов
/ 20 марта 2017

Функция готовности, основанная на ответе с самым высоким рейтингом:

  /**
   * Check if date exists and is valid.
   *
   * @param {String} dateString Date in YYYY-mm-dd format.
   */
  function isValidDate(dateString) {
  var isValid = false;
  var date;

  date =
    new Date(
      dateString);

  if (
    Object.prototype.toString.call(
      date) === "[object Date]") {

    if (isNaN(date.getTime())) {

      // Date is unreal.

    } else {
      // Date is real if month and day match each other in date and string (otherwise may be shifted):
      isValid =
        date.getUTCMonth() + 1 === dateString.split("-")[1] * 1 &&
        date.getUTCDate() === dateString.split("-")[2] * 1;
    }
  } else {
    // It's not a date.
  }

  return isValid;
}
2 голосов
/ 13 августа 2013

Date object to string - более простой и надежный способ определить, являются ли оба поля действительной датой. например Если вы введете это «-------» в поле ввода даты. Некоторые из приведенных выше ответов не будут работать.

jQuery.validator.addMethod("greaterThan", 

    function(value, element, params) {
        var startDate = new Date($(params).val());
        var endDate = new Date(value);

        if(startDate.toString() === 'Invalid Date' || endDate.toString() === 'Invalid Date') {
            return false;
        } else {
            return endDate > startDate;
        }
    },'Must be greater than {0}.');
2 голосов
/ 23 августа 2015
function isValidDate(strDate) {
    var myDateStr= new Date(strDate);
    if( ! isNaN ( myDateStr.getMonth() ) ) {
       return true;
    }
    return false;
}

Назовите это так

isValidDate(""2015/5/2""); // => true
isValidDate(""2015/5/2a""); // => false
1 голос
/ 11 августа 2011

Я думаю, что это длительный процесс. Мы можем сократить его, как показано ниже:

 function isValidDate(dateString) {
        debugger;
        var dateStringSplit;
        var formatDate;

        if (dateString.length >= 8 && dateString.length<=10) {
            try {
                dateStringSplit = dateString.split('/');
                var date = new Date();
                date.setYear(parseInt(dateStringSplit[2]), 10);
                date.setMonth(parseInt(dateStringSplit[0], 10) - 1);
                date.setDate(parseInt(dateStringSplit[1], 10));

                if (date.getYear() == parseInt(dateStringSplit[2],10) && date.getMonth()+1 == parseInt(dateStringSplit[0],10) && date.getDate() == parseInt(dateStringSplit[1],10)) {
                    return true;
                }
                else {
                    return false;
                }

            } catch (e) {
                return false;
            }
        }
        return false;
    }
1 голос
/ 23 апреля 2015
function isValidDate(date) {
  return !! (Object.prototype.toString.call(date) === "[object Date]" && +date);
}
1 голос
/ 26 августа 2014

Обычно я придерживаюсь любой имплантации даты в стеке браузера. Это означает, что вы всегда получите «Неверную дату» при вызове toDateString () в Chrome, Firefox и Safari на дату этого ответа.

if(!Date.prototype.isValidDate){
  Date.prototype.isValidDate = function(){
    return this.toDateString().toLowerCase().lastIndexOf('invalid') == -1;
  };
}

Я не проверял это в IE, хотя.

1 голос
/ 08 ноября 2013

Для компонентов даты на основе int 1:

var is_valid_date = function(year, month, day) {
    var d = new Date(year, month - 1, day);
    return d.getFullYear() === year && (d.getMonth() + 1) === month && d.getDate() === day
};

Тесты:

    is_valid_date(2013, 02, 28)
&&  is_valid_date(2016, 02, 29)
&& !is_valid_date(2013, 02, 29)
&& !is_valid_date(0000, 00, 00)
&& !is_valid_date(2013, 14, 01)
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...