编写一个正则表达式,其输出仅是 01/03/2021 - 01/03/2020 范围内的行

编写一个正则表达式,其输出仅是 01/03/2021 - 01/03/2020 范围内的行

我有一个文件,其日期从 01/01/2020 到 04/04/2021 我想通过使用egrep 仅获取 01/03/2020 到 01/03/2021 之间的日期。我尝试做

egrep "([0][1-9]|[1-2][0-9]|[3][0]/[0][3-9]|[1][0-2]/[2][0][2][0-1])$" dates.txt

但它仍然给我文件中的所有日期:

$ cat dates.txt 
01/01/2020
24/01/2020
04/02/2020
23/02/2020
01/03/2020
13/03/2020
14/04/2020
29/05/2020
16/06/2020
17/07/2020
18/08/2020
19/09/2020
20/10/2020
21/11/2020
22/12/2020
23/01/2021
24/02/2021
01/03/2021
25/03/2021
04/04/2021

答案1

使用给出的示例文件,其中日期按顺序排列,并且开始日期和结束日期都存在于文件中,您可能会发现awk更简单的解决方案。

$ awk '$1=="01/03/2020",$1=="01/03/2021"' dates.txt
01/03/2020
13/03/2020
14/04/2020
29/05/2020
16/06/2020
17/07/2020
18/08/2020
19/09/2020
20/10/2020
21/11/2020
22/12/2020
23/01/2021
24/02/2021
01/03/2021
$

顺便说一句,请注意使用的egrep已弃用,支持符合 POSIX 的grep -E方法。

答案2

我真的不会尝试仅使用正则表达式来做到这一点。更复杂的工具会让事情变得更容易。例如,使用awk

$ awk -F/ '($3==2020 && $2 > 2) || ($3==2021 && ($2 < 3) || ($1< 2 && $2 == 3))' dates.txt 
01/03/2020
13/03/2020
14/04/2020
29/05/2020
16/06/2020
17/07/2020
18/08/2020
19/09/2020
20/10/2020
21/11/2020
22/12/2020
23/01/2021
24/02/2021
01/03/2021

awk字段分隔符设置为/,然后简单地选择与这三个条件之一匹配的行:

  • 最后一个字段(年份)是2020,第二个字段(月份)大于2。这将匹配从01/03/2020到 的所有日期31/12/2020
  • 最后一个字段(年份)是2021并且
    • 第二个字段(月份)小于3OR
    • 第一个字段(月份中的某一天)小于2,第二个字段(月份)正好是3

答案3

根据您的描述,您需要 2020 年之后的任何日期01/03/2020。那将是:

$ egrep "(../(0[3-9]|1[0-2])/2020$)" dates.txt

还有从 2021 年至今的所有日期01/03/2021。那部分是:

$ egrep "((/0[1-2]/|01/03/)2021$)" dates.txt

连接两个范围:

$ egrep "(../(0[3-9]|1[0-2])/2020$|(/0[1-2]/|01/03/)2021$)" dates.txt

稍微简化一下,更改为grep -E(现在相当于egrep),并列出输出:

$ grep -E "(/(0[3-9]|1[0-2])/2020|(/0[1-2]/|01/03/)2021)$" dates.txt
01/03/2020
13/03/2020
14/04/2020
29/05/2020
16/06/2020
17/07/2020
18/08/2020
19/09/2020
20/10/2020
21/11/2020
22/12/2020
23/01/2021
24/02/2021
01/03/2021

您的源文件似乎是:

$ cat dates.txt 
01/01/2020
24/01/2020
04/02/2020
23/02/2020
01/03/2020
13/03/2020
14/04/2020
29/05/2020
16/06/2020
17/07/2020
18/08/2020
19/09/2020
20/10/2020
21/11/2020
22/12/2020
23/01/2021
24/02/2021
01/03/2021
25/03/2021
04/04/2021

答案4

只需使用 awk:

$ awk -F'/' '{d=$3$2$1} (20200301 <= d) && (d <= 20210301)' dates.txt
01/03/2020
13/03/2020
14/04/2020
29/05/2020
16/06/2020
17/07/2020
18/08/2020
19/09/2020
20/10/2020
21/11/2020
22/12/2020
23/01/2021
24/02/2021
01/03/2021

无论输入是否排序以及输入中是否存在范围分隔日期,上述内容都将起作用。

只需更改<=为“<如果between您的意思是排除分隔日期”即可。

相关内容