Проверка даты в оболочке

14

Я хочу проверить приведенный ниже формат даты в сценарии оболочки

2015-Jul-13

Я использую, date -d "2015-Jul-13" +"%Y-%b-%d"но дает ошибку как

date: invalid date '2015-Jul-13'
чхайа вишвакарма
источник
@Pandya: OP ясно о его / ее вопросе. ОП хочет проверить (проверить правильность введенной даты) указанного формата даты, но сообщает, что введенная дата недействительна.
Туши
GNU dateне распознает YYYY-MMM-DD. Не могли бы вы использовать YYYY-MM-DDили DD MMM YYYYвместо?
Ройма
Я уверен at, что да, и - я думаю - touchтоже. Я написал функцию оболочки проверки даты, основанную на одном разе touch... Нет, нет touch- она ​​обрабатывает только цифры, но atвыполняет довольно глубокий анализ ...
mikeserv
@Thushi давайте проясним лишний комментарий нами
Pandya
6
Неправильное прочтение названия: Дата проверки - это ад
Адам Дэвис

Ответы:

12

GNU dateне поддерживает YYYY-MMM-DD. Тем не менее, он понимает DD-MMM-YYYY. Так что если вам действительно нужно обрабатывать даты этого формата, вы можете сделать это с помощью чего-то подобного, что просто меняет аргументы на ожидаемый формат date:

ymd='2015-Jul-13'

dmy=$(echo "$ymd" | awk -F- '{ OFS=FS; print $3,$2,$1 }')
if date --date "$dmy" >/dev/null 2>&1
then
    echo OK
fi

Вот решение всей оболочки. Разбивая его, IFS=-инструкции говорят оболочке разделить предстоящую командную строку на дефис -вместо пробела. set $ymdРазбирает $ymdпеременную как для командной строки, но теперь расщепляется с помощью дефиса, присвоения значений параметров $1, $2 и сл . echo "$3-$2-$1"Тривиальные выводят три захваченных значений в обратном порядке.

ymd='2015-Jul-13'

dmy=$(IFS=-; set $ymd; echo "$3-$2-$1")
if date --date "$dmy" >/dev/null 2>&1
then
    echo OK
fi
roaima
источник
@mikeserv: круто! Это сработало: ymd=$(IFS=-;set $ymd; echo "$3-$2-$1") Не могли бы вы раскрыть магию, стоящую за setкомандой?
Joepd
11

С manpage: -

DATE STRING
       The --date=STRING is a mostly free format human readable date string such as "Sun, 29 Feb 2004 16:21:42 -0800"
       or  "2004-02-29  16:21:42" or even "next Thursday".  A date string may contain items indicating calendar date,
       time of day, time zone, day of week, relative time, relative date, and numbers.  An empty string indicates the
       beginning  of  the  day.   The  date string format is more complex than is easily documented here but is fully
       described in the info documentation.

Но, похоже, не распознают YYYY-MMM-DDформат. Таким образом, вы можете использовать либо снизу или аналогичные, как:

$ date -d "2015-07-13" +"%Y-%b-%d"
2015-Jul-13
$ date -d "Jul 13 2015" +"%Y-%b-%d"
2015-Jul-13
$ date -d "13 Jul 2015" +"%Y-%b-%d"
2015-Jul-13

ИЛИ вы должны конвертировать / переформатировать его перед отправкой в date!

Также смотрите Как вы определяете формат для ввода на сегодняшний день?


Рекомендую посетить: Форматы ввода даты .

Вот правила.

Для числовых месяцев разрешен формат ISO 8601 «год-месяц-день», где год - любое положительное число, месяц - число от 01 до 12, а день - число от 01 до 31. Должен присутствовать начальный ноль. если число меньше десяти. Если год 68 или меньше, то к нему добавляется 2000; в противном случае, если год меньше 100, к нему добавляется 1900. Популярна в США конструкция «месяц / день / год». Также «месяц / день», пропуская год.

Буквальные месяцы могут быть указаны полностью: «январь», «февраль», «март», «апрель», «май», «июнь», «июль», «август», «сентябрь», «октябрь», « Ноябрь или декабрь. Буквальные месяцы могут быть сокращены до первых трех букв, за которыми может следовать сокращенная точка. Также разрешено писать «сентябрь» вместо «сентябрь».

Если месяцы записаны буквально , календарная дата может быть указана в виде любого из следующего:

 день месяц год
 день месяц
 месяц день год
 день месяц месяц

подчеркнуто мной

Здесь вы можете видеть, что нет такого формата, как год-месяц-день ! (месяцами написаны буквально)

Pandya
источник
7

С помощью zshвы можете использовать strftimeвстроенный (доступно через zsh/datetime) с -r(реверс):

strftime -r формат временной строки

который использует формат для анализа временной строки и вывода количества секунд с начала эпохи:

zmodload zsh/datetime
strftime -r %Y-%b-%d 2015-Jul-13
1436734800

Это ошибки, если дата недействительна:

strftime -r %Y-%b-%d 2015-Jul-33
zsh: strftime: 5: формат не соответствует

Вы также можете конвертировать секунды с начала эпохи в любой другой стандартный / пользовательский формат даты, например

strftime '%A, %B %d, %Y' 1447970400
Пятница, 20 ноября 2015 г.
don_crissti
источник