在Shell脚本中获取上个月最后一天的日期


11

如何根据处理日期获得上个月的结束日期?

例子:

  • 处理日期= 2015年1月15日
  • 预计日期= 2014年12月31日,

  • 处理日期= 2015年2月10日
  • 预计日期= 2015年1月31日

Answers:


27

使用GNU date

$ date +%d%b%Y
16Aug2015
$ date -d "$(date +%Y-%m-01) -1 day" +%d%b%Y
31Jul2015

某些shell内置了对日期操作的支持:

ksh93

$ printf "%(%d%b%Y)T\n" "1st day, yesterday"
31Jul2015

zsh

$ zmodload zsh/datetime
$ strftime -s d %Y-%m-01-12 $EPOCHSECONDS
$ strftime -rs d %Y-%m-%d-%H $d
$ strftime %d%b%Y $((d-86400))
31Jul2015

4

很多方法可以做到这一点。这是我找到的最简单的一个(这里假设GNU date):

$ date -d "-$(date +%d) days"
Fri Jul 31 16:07:23 EDT 2015

1
@stephane的答案更清楚,并且在某些奇怪的年份(在月中跳过/添加日期的日子)中,这一方法将行不通。是的,这已经发生了。参见youtube.com/watch?v=-5wpm-gesOY
ctrl-alt-delor

@richard,顺便GNU日期一天偏移工作(1天偏移是不一样的24小时的一个),我觉得这个答案,我的应该是等价的,只有在将跳过一个月份的最后一天时区失败(通常情况下,如果曾经发生了这很可能是在一些太平洋岛屿的开关-12:00偏移至12:00抵消(或-13至11 ...)...
斯特凡Chazelas

@Stephane感谢您指出其他问题,时间很困难。请注意,在解决方案中,如果删除了月中(发生这种情况),则30天不是30天,因此减去30不会使您到达上个月的最后一天。如果每月的第一天(无法保证),我将看不到为什么这将不起作用。但是,这并不意味着会。
ctrl-alt-delor

@richard,请参阅TZ=Pacific/Apia faketime '2011-12-31 12:00' date -d '1 day ago'。您收到错误消息,因为那里没有2011-12-30。也就是说,日期偏移是在日历时间上完成的。2011-12-31减去31天将为您提供2011-11-30,因为它使31减少31。当前时间不减少31 * 24 * 60 * 60 * 60秒。与TZ=Pacific/Apia faketime '2011-12-31 12:00' date -d '24 hour ago'此相比,第29天,即这次,它是24 * 60 * 60 * 60秒前的日期。
斯特凡Chazelas

2

这是在Mac OS上使用BSD date实用程序的版本:

date -v1d -v-1d +%d%b%Y

参数按顺序应用。您可以想象一下,日期是从一个参数传递到下一个参数的。例如:

  • 从当前日期开始(date)-> 2017-03-06
  • 将日期设置为该月的第一天(-v1d)-> 2017-03-01
  • 从中减去一日(-v-1d)-> 2017-02-28
  • 格式化日期(+%d%b%Y)-> 2017年2月28日

您可以使用来达到任意数量的前进或后退月份date -v-1m -v1d -v-1d,而用所需的前进或后退-1m月份数(+1m)代替。

这就是通用答案。该问题专门询问有关开始日期的日期。Mac OS / BSD日期实用程序不允许您提供起始日期戳,但可以单独设置每个日期元素:

date -v2015y -v1m -v15d -v1d -v-1d +%d%b%Y -> 2014年12月31日


0

尝试使用此代码

date -d "-$(date +%d) days  month" +%Y-%m-%d

这使的最后一天这个月。
沃伦·扬
By using our site, you acknowledge that you have read and understand our Cookie Policy and Privacy Policy.
Licensed under cc by-sa 3.0 with attribution required.