如何使用正则表达式提取文件名并检查是否存在



我有一个文件myfile.log看起来像这样:

 RS |         hello.txt|        OK|      INFO| [CATLG]
==============================================
 A4 |        byebye.txt|        OK|      INFO| [DELETE]
==============================================
Most common:
----------------------------------------------
 AS | stackoverflow.txt|        OK|      INFO| [CATLG]

然后我尝试创建一个脚本来提取与正则表达式匹配的文件:

s(.+)|s+OK|s+INFO|s+[CATLG

最后检查该文件是否存在于/myfiles/record/目录中。如果没有,将在文件名前打印一个 D。

下面是一个输出示例,假设stackoverflow.txt存在而hello.txt不存在:

  hello.txt
D stackoverflow.txt

我尝试使用 grep 函数,但如果我这样做:

grep -oh 's.+|s+OK|s+INFO|s+[CATLG' myfile.log | uniq -i

不返回任何内容。我做错了什么?你有什么想法吗?

grep 的正则表达式不支持正则表达式中的s。您可以使用grep -P (PCRE)口味:

grep -oPh 's.+|s+OK|s+INFO|s+[CATLG' myfile.log 

或者将您的正则表达式转换为 ERE:

egrep -oh '[[:blank:]].+|[[:blank:]]+OK|[[:blank:]]+INFO|[[:blank:]]+[CATLG' myfile.log 

要仅打印文件名,请使用:

grep -oPh '[^|]+|s+K[^|]+(?=|s+OK.*?[CATLG)' file
hello.txt
stackoverflow.txt
awk -F '|' '/|/ {fname=gensub(" ","","g",$1)
                 if ( system( "[ -f " fname " ] " ) ) {
                 print "D " fname }
                 else {
                     print "  " fname }
           }' INPUTFILE

可能适合您。

  1. 将输入字段分隔符设置为 |
  2. 仅在具有 | s 的线路上工作
  3. fname变量设置为第一个字段的剥离版本
  4. 向外壳程序调用测试命令 ( [
grep -oP '|s*KS+(?=|s+OK.*CATLG)' | 
while read file; do
    [[ -f /myfiles/record/"$file" ]] && flag="" || flag=D
    printf "%-2s%sn" "$flag" "$file"
done

解释:

  • grep 命令使用 (-P) perl 正则表达式语法,并且只输出匹配的文本 (-o),每个匹配项都在自己的行上。
    • K指令的意思是"忘记刚刚匹配的东西" - 这是一种获得可变长度的后视的方法。
    • 我发现后面跟着非空格字符:管道、空格、"OK"、一些字符和"CATLG"
  • grep 输出通过管道传输到 while 循环中
  • 我将文件名读入名为 file 的变量中
  • 我使用条件命令 [[-f 运算符来查看文件是否存在。
  • 如果确实存在,则执行&&运算符之后的命令,否则如果文件不存在,则执行||运算符之后的命令。
  • 最后,我以OP所需的格式打印输出。

相关内容

  • 没有找到相关文章

最新更新