R: Проверить, действительна ли дата - PullRequest
0 голосов
/ 18 июня 2020

Предположим, что дата задана как три целых числа: год, месяц, день

Год - это целое число 4 di git (например, 2020), месяц находится в диапазоне от 1 до 12, день превышает 1 -31.

Я ищу простую функцию (назовите ее checkdate), которая может проверять, действительна ли дата, возвращая ИСТИНА, если действительна, и ЛОЖЬ, если недействительна.

Например, checkdate (2008, 2, 29) вернет ИСТИНА, потому что 2008 год был високосным.

С другой стороны, checkdate (2009, 2, 29) вернет ЛОЖЬ, потому что 2009 год не был високосным.

checkdate (2009, 6, 31) вернет FALSE, потому что в июне всего 30 дней.

Et c.

UPDATE

На основе Ответ Дирка, ниже, вот функция, которая выполняет то, что я просил:

    checkdate = function(y, m, d) {
        #y: A year, not abbreviated to 2 digits.
        #m: An integer in the range 1-12.
        #d: An integer in the range 1-31.

        #Convert to an R Date object.
        #If the date is not valid, NA is returned.
        dt = as.Date(paste(y, m, d, sep='-'), optional=TRUE)

        ifelse(is.na(dt), FALSE, TRUE)
    }

Ответы [ 3 ]

2 голосов
/ 18 июня 2020

Попробуйте преобразовать входные данные в дату, если не удалось вернуть FALSE.

checkdate <- function(y, m, d) {
    tryCatch(lubridate::is.Date(as.Date(paste(y, m, d, sep = '-'))), 
             error = function(e) return(FALSE))
}

checkdate(2009, 6, 31)
#[1] FALSE
checkdate(2009, 2, 29)
#[1] FALSE
checkdate(2008, 2, 29)
#[1] TRUE
0 голосов
/ 18 июня 2020

Base R с использованием логики @Ronak Shah c:

checkdate <- function(y, m, d) {
  tryCatch(inherits(as.Date(paste(y, m, d, sep = '-')), "Date"), 
           error = function(e) return(FALSE))
}
checkdate(2015, 12, 31)
0 голосов
/ 18 июня 2020

Конечно. Просто попробуйте разобрать его:

R> days <- 28:31
R> dates <- paste0("2020-02-", days)
R> as.Date(dates)
[1] "2020-02-28" "2020-02-29" NA           NA          
R> 

Это показывает, что в 2020 году существовали 28 и 29 февраля (високосный год), но не 30 и 31.

Из ваших трех векторов вы могли бы использовать sprintf("%4d-%02d-%02", y, m, d) для создания вектора входных текстов для анализа.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...