在 Bash 中解析日期
声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow
原文地址: http://stackoverflow.com/questions/1842634/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me):
StackOverFlow
Parse Date in Bash
提问by Steve
How would you parse a date in bash, with separate fields (years, months, days, hours, minutes, seconds) into different variables?
您将如何将 bash 中的日期解析为不同的变量,将单独的字段(年、月、日、小时、分钟、秒)解析为不同的变量?
The date format is: YYYY-MM-DD hh:mm:ss
日期格式为: YYYY-MM-DD hh:mm:ss
回答by Dirk Eddelbuettel
Does it have to be bash? You can use the GNU coreutils /bin/date
binary for many transformations:
它必须是bash吗?您可以使用 GNU coreutils/bin/date
二进制文件进行许多转换:
$ date --date="2009-01-02 03:04:05" "+%d %B of %Y at %H:%M and %S seconds"
02 January of 2009 at 03:04 and 05 seconds
This parses the given date and displays it in the chosen format. You can adapt that at will to your needs.
这将解析给定的日期并以所选格式显示它。您可以根据自己的需要随意调整。
回答by NVRAM
This is simple, just convert your dashes and colons to a space (no need to change IFS) and use 'read' all on one line:
这很简单,只需将破折号和冒号转换为空格(无需更改 IFS)并在一行中使用“全部读取”:
read Y M D h m s <<< ${date//[-:]/ }
For example:
例如:
$ date=$(date +'%Y-%m-%d %H:%M:%S')
$ read Y M D h m s <<< ${date//[-: ]/ }
$ echo "Y=$Y, m=$m"
Y=2009, m=57
回答by Chaim Leib Halbert
I had a different input time format, so here is a more flexible solution.
我有不同的输入时间格式,所以这里有一个更灵活的解决方案。
Convert dates in BSD/macOS
在 BSD/macOS 中转换日期
date -jf in_format [+out_format] in_date
where the formats use strftime (see man strftime
).
其中格式使用 strftime(请参阅 参考资料man strftime
)。
For the given input format YYYY-MM-DD hh:mm:ss
:
对于给定的输入格式YYYY-MM-DD hh:mm:ss
:
$ date -jf '%Y-%m-%d %H:%M:%S' '2017-05-10 13:40:01'
Wed May 10 13:40:01 PDT 2017
To read them into separate variables, I'm taking NVRAM's idea, but allowing you to use any strftime format:
为了将它们读入单独的变量,我采用了 NVRAM 的想法,但允许您使用任何 strftime 格式:
$ date_in='2017-05-10 13:40:01'
$ format='%Y-%m-%d %H:%M:%S'
$ read -r y m d H M S <<< "$(date -jf "$format" '+%Y %m %d %H %M %S' "$date_in")"
$ for var in y m d H M S; do echo "$var=${!var}"; done
y=2017
m=05
d=10
H=13
M=40
S=01
In my case, I wanted to convert between timezones (see your /usr/share/zoneinfo
directory for zone names):
就我而言,我想在时区之间进行转换(请参阅您的/usr/share/zoneinfo
目录以获取区域名称):
$ format=%Y-%m-%dT%H:%M:%S%z
$ TZ=UTC date -jf $format +$format 2017-05-10T02:40:01+0200
2017-05-10T00:40:01+0000
$ TZ=America/Los_Angeles date -jf $format +$format 2017-05-10T02:40:01+0200
2017-05-09T17:40:01-0700
Convert dates in GNU/Linux
在 GNU/Linux 中转换日期
On a Mac, you can install the GNU version of
date
asgdate
withbrew install coreutils
.
在Mac上,你可以安装GNU版本
date
为gdate
使用brew install coreutils
。
date [+out_format] -d in_date
where the out_format uses strftime (see man strftime
).
其中 out_format 使用 strftime(请参阅 参考资料man strftime
)。
In GNU coreutils' date
command, there is no way to explicitly set an input format, since it tries to figure out the input format by itself, and stuff usually just works. (For detail, you can read the manual at coreutils: Date input formats.)
在 GNU coreutils 的date
命令中,没有办法明确设置输入格式,因为它试图自己找出输入格式,而这些东西通常都能正常工作。(有关详细信息,您可以阅读coreutils 中的手册:日期输入格式。)
For example:
例如:
$ date '+%Y %m %d %H %M %S' -d '2017-05-10 13:40:01'
2017 05 10 13 40 01
To read them into separate variables:
要将它们读入单独的变量:
$ read -r y m d H M S <<< "$(date '+%Y %m %d %H %M %S' -d "$date_in")"
To convert between timezones (see your /usr/share/zoneinfo
directory for zone names), you can specify TZ="America/Los_Angeles"
right in your input string. Note the literal "
chars around the zone name, and the space character before in_date:
要在时区之间进行转换(请参阅您的/usr/share/zoneinfo
目录以获取区域名称),您可以TZ="America/Los_Angeles"
在输入字符串中正确指定。注意"
区域名称周围的文字字符,以及 in_date 之前的空格字符:
TZ=out_tz date [+out_format] 'TZ="in_tz" in_date'
For example:
例如:
$ format='%Y-%m-%d %H:%M:%S%z'
$ TZ=America/Los_Angeles date +"$format" -d 'TZ="UTC" 2017-05-10 02:40:01'
2017-05-09 19:40:01-0700
$ TZ=UTC date +"$format" -d 'TZ="America/Los_Angeles" 2017-05-09 19:40:01'
2017-05-10 02:40:01+0000
GNU date also understands hour offsets for the time zone:
GNU date 也了解时区的小时偏移量:
$ TZ=UTC date +"$format" -d '2017-05-09 19:40:01-0700'
2017-05-10 02:40:01+0000
回答by DigitalRoss
$ t='2009-12-03 12:38:15'
$ a=(`echo $t | sed -e 's/[:-]/ /g'`)
$ echo ${a[*]}
2009 12 03 12 38 15
$ echo ${a[3]}
12
回答by Steve Baker
The array method is perhaps better, but this is what you were specifically asking for:
数组方法可能更好,但这是您特别要求的:
IFS=" :-"
read year month day hour minute second < <(echo "YYYY-MM-DD hh:mm:ss")
回答by Paused until further notice.
Pure Bash:
纯重击:
date="2009-12-03 15:35:11"
saveIFS="$IFS"
IFS="- :"
date=($date)
IFS="$saveIFS"
for field in "${date[@]}"
do
echo $field
done
2009
12
03
15
35
11
回答by Vijay
instead of using the shell scripting,incorporate in your scripting itself like below wheever you need:
不使用 shell 脚本,而是在您需要的时候像下面这样合并到您的脚本中:
a=date +%Y
b=date +%S
c=date +%H
a will be year b will be seconds c will be hours. and so on.
a 将是年 b 将是秒 c 将是小时。等等。
回答by Lri
Another solution to the OP's problem:
OP问题的另一种解决方案:
IFS=' -:' read y m d h m s<<<'2014-03-26 16:36:41'
Converting a date to another format with BSD date
and GNU date
:
使用 BSDdate
和 GNU将日期转换为另一种格式date
:
$ LC_ALL=C date -jf '%a %b %e %H:%M:%S %Z %Y' 'Wed Mar 26 16:36:41 EET 2014' +%F\ %T
2014-03-26 16:36:41
$ gdate -d 'Wed Mar 26 16:36:41 EET 2014' +%F\ %T
2014-03-26 16:36:41
GNU date
recognizes Wed
and Mar
even in non-English locales but BSD date
doesn't.
GNUdate
识别Wed
和Mar
即使在非英语语言环境,但BSDdate
没有。
Converting seconds since epoch to a date and time with GNU date and BSD date:
将自纪元以来的秒数转换为具有 GNU 日期和 BSD 日期的日期和时间:
$ gdate -d @1234567890 '+%F %T'
2009-02-14 01:31:30
$ date -r 1234567890 '+%F %T'
2009-02-14 01:31:30
Converting seconds to hours, minutes, and seconds with a POSIX shell, POSIX awk
, GNU date
, and BSD date
:
使用 POSIX shell、POSIX awk
、GNUdate
和 BSD将秒转换为小时、分钟和秒date
:
$ s=12345;printf '%02d:%02d:%02d\n' $((s/3600)) $((s%3600/60)) $((s%60))
05:25:45
$ echo 12345|awk '{printf "%02d:%02d:%02d\n",$ t=12345678
$ printf '%d:%02d:%02d:%02d\n' $((t/86400)) $((t/3600%24)) $((t/60%60)) $((t%60))
142:21:21:18
/3600,$ d="2009-12-03 15:35:11"
$ d=${d//[- :]/|}
$ IFS="|"
$ set -- $d
$ echo
2009
$ echo
12
$ echo $@
2009 12 03 15 35 11
%3600/60,##代码##%60}'
05:25:45
$ gdate -d @12345 +%T
05:25:45
$ date -r 12345 +%T
05:25:45
Converting seconds to days, hours, minutes, and seconds:
将秒转换为天、小时、分钟和秒:
##代码##回答by ghostdog74
another pure bash
另一个纯粹的 bash
##代码##回答by Jay
have you tried using cut?
something like this:
dayofweek=date|cut -d" " -f1
你试过用 cut 吗?像这样:dayofweek=date|cut -d" " -f1