bash 中的日历计算

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/705857/
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

提示:将鼠标放在中文语句上可以显示对应的英文。显示中英文
时间:2020-09-17 20:47:31  来源:igfitidea点击:

Calendar calculations in bash

linuxbashshellcommand-line

提问by Guss

I want to do some calendar manipulations in bash - specifically, I want to figure out the last date of a given month (including leap-year, and a preparing a table for a lookup is not a valid solution for me).

我想在 bash 中进行一些日历操作 - 具体来说,我想找出给定月份的最后日期(包括闰年,并且为查找准备表对我来说不是一个有效的解决方案)。

Supposedly I have the following code:

据说我有以下代码:

$year=2009
$start_month=2
$end_month=10
for $month in $(seq $start_month $end_month); do
  echo "Last date of "$(date +"%B" -d "${year}-${month}-01")" is: " ???
done

I can't figure out how to do something like this. I though date -dwould work like POSIX mktime and fold invalid dates to their valid equivalents, so I could say something like date -d "2009-03-00"and get '2009-02-28', but no such luck.

我不知道如何做这样的事情。我虽然date -d会像 POSIX mktime 一样工作并将无效日期折叠到有效的等价物,所以我可以说类似的话date -d "2009-03-00"并得到“2009-02-28”,但没有这样的运气。

Is there anyway to do it using only what is available on bash in a standard GNU environment?

有没有办法只使用标准 GNU 环境中 bash 上可用的内容?

回答by Steve Baker

Try: date -d 'yesterday 2009-03-01'

尝试: date -d 'yesterday 2009-03-01'

Intuitive I know. Earlier versions of date used to work the POSIX way.

直觉我知道。早期版本的 date 用于以 POSIX 方式工作。

回答by lhunath

date(1)'s -d is GNU specific; so using that will only work on GNU Linux.

date(1) 的 -d 是 GNU 特定的;所以使用它只能在 GNU Linux 上工作。

A more portable solution (this should even work in shAFAIK), is this:

一个更便携的解决方案(这甚至应该适用于shAFAIK),是这样的:

: $(cal 4 2009); echo $_

回答by mouviciel

If you don't mind playing with grep/awk/perl, you can take a look at cal.

如果你不介意玩 grep/awk/perl,你可以看看cal.

$ cal 4 2009
     April 2009
Su Mo Tu We Th Fr Sa 
          1  2  3  4
 5  6  7  8  9 10 11
12 13 14 15 16 17 18
19 20 21 22 23 24 25
26 27 28 29 30

Edit (MarkusQ): To atone for my joke solution below I'll contribute to yours:

编辑(MarkusQ):为了弥补我下面的笑话解决方案,我将为您的解决方案做出贡献:

cal 4 2009 | tr ' ' '\n' | grep -v ^$ | tail -n 1

回答by MarkusQ

Well, one way would be to watch the current date in a loop until the month component changes, saving the day component for one round. That would give you both the first and last day of the month, but it might be too slow.

嗯,一种方法是循环观察当前日期,直到月份组件发生变化,将日期组件保存为一轮。这会给你当月的第一天和最后一天,但它可能太慢了。

Posted 1 April 2009

2009 年 4 月 1 日发布