【问题标题】:Finding files with names matching regex and current date in a script在脚本中查找名称与正则表达式和当前日期匹配的文件
【发布时间】:2019-11-27 12:45:25
【问题描述】:

我想在目录中查找前一天的文件(即昨天:/daily-2019-11-26/photo-2019-11-26-15-processed.jpg 应该匹配,/daily-2019-11-26/photo-2019-11-26-02-processed.jpg 不应该匹配)。

如果我在终端中输入它,它会按预期工作

find /daily-$(date -d "-1 day" +%F)/photo-$(date -d "-1 day" +%F)-!(0[0-9])-*.jpg

#                                                                 ^ not 00-09 a.m. hours

但是当我像bash script.sh 一样运行脚本文件时它不能在脚本文件中工作

#!/bin/bash
find /daily-$(date -d "-1 day" +%F)/photo-$(date -d "-1 day" +%F)-!(0[0-9])-*.jpg

我收到错误:line 2: syntax error near unexpected token '('

怎么了?

最后我想每天用一个 cron 运行这个脚本

【问题讨论】:

  • 为什么第一个例子应该匹配而第二个不应该?
  • @Toto 因为我想在文件名中排除 00-09 小时:photo-2019-11-26-15-processed.jpg 标记为 15 小时,photo-2019-11-26-02-已处理的.jpg 标记为 02 小时

标签: regex bash shell date find


【解决方案1】:

我收到错误:line 2: syntax error near unexpected token '(' 怎么了?

在您的 script.sh 文件中添加 shopt -s extglob 以启用扩展模式匹配。

例如:

#!/bin/bash
shopt -s extglob
find /daily-$(date -d "-1 day" +%F)/photo-$(date -d "-1 day" +%F)-!(0[0-9])-*.jpg

为什么你在终端输入了它,但在script.sh 输入失败了?

extglob 被设置为on,因此扩展模式匹配部分,即!(0[0-9]),被正确解释。但是,您必须在每个 .sh 脚本文件中启用它,因为它默认是关闭的。

顺便说一句。你可以在终端输入shopt extglob,查看extglobon还是off


其他注意事项:

引用命令替换:

尽管考虑到您的date 命令返回的值的格式并非完全必要),但请考虑在您的find 命令中双引号command substitution,如下所示:

#!/bin/bash
shopt -s extglob
find /daily-"$(date -d "-1 day" +%F)"/photo-"$(date -d "-1 day" +%F)"-!(0[0-9])-*.jpg

#           ^                       ^       ^                       ^

改用ls

您也可以使用ls 而不是find 获得相同的结果(鉴于您的问题find 实际上似乎没有必要):

例如:

#!/bin/bash
shopt -s extglob
ls /daily-"$(date -d "-1 day" +%F)"/photo-"$(date -d "-1 day" +%F)"-!(0[0-9])-*.jpg

重构

因为你在调用; date -d "-1 day" +%F 两次,您可以将其分配给变量,然后稍后引用它。这样做只会调用一次date 命令。例如下面我们将昨天的日期分配给任意命名的变量yyyy_mm_dd_yesterday

  • 使用find:

    #!/bin/bash
    shopt -s extglob
    yyyy_mm_dd_yesterday=$(date -d "-1 day" +%F)
    find /daily-"$yyyy_mm_dd_yesterday"/photo-"$yyyy_mm_dd_yesterday"-!(0[0-9])-*.jpg
    
  • 使用ls

    #!/bin/bash
    shopt -s extglob
    yyyy_mm_dd_yesterday=$(date -d "-1 day" +%F)
    ls /daily-"$yyyy_mm_dd_yesterday"/photo-"$yyyy_mm_dd_yesterday"-!(0[0-9])-*.jpg
    

补充说明:

您在script.sh 中定义的路径名,即读取/daily ... 的部分,需要是script.sh 所在位置的相对路径名,或者是目录的绝对路径名。

【讨论】:

    【解决方案2】:

    “查找”并不是真正必要的,因为 bash 模式会执行所有工作。仅考虑 bash 解决方案:

    shopt -s extglob
    DD=$(date -d "-1 day" +'%F')
    ls /daily-$DD/photo-$DD-!(0[0-9])-*.jpg
    

    或者,使用标准模式(不需要 extglob) - 我不应该这样做,因为问题不清楚选择规则,并且没有为测试提供输入。

    DD=$(date -d "-1 day" +'%F')
    ls /daily-$DD/photo-$DD-[12][0-9])-*.jpg
    

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2020-03-05
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2015-04-29
      • 1970-01-01
      相关资源
      最近更新 更多