Regex 多线模式匹配
我有一些文件的内容如下: 文件1:Regex 多线模式匹配,regex,bash,Regex,Bash,我有一些文件的内容如下: 文件1: AAA BBB CCC 123 文件2: AAA BBB 123 我只想在前3行是字母或上面示例中的“file1”时回显文件名。 我把3行合并成一行,并将其与我的正则表达式[A-Z]进行比较,但由于某种原因,无法使其匹配 我的剧本: file=file1 if [[ $(head -3 $file|tr -d '\n'|sed 's/\r//g') == [A-Z] ]]; then echo "$file" fi 我用bash-x运行了
AAA
BBB
CCC
123
文件2:
AAA
BBB
123
我只想在前3行是字母或上面示例中的“file1”时回显文件名。
我把3行合并成一行,并将其与我的正则表达式[A-Z]进行比较,但由于某种原因,无法使其匹配
我的剧本:
file=file1
if [[ $(head -3 $file|tr -d '\n'|sed 's/\r//g') == [A-Z] ]]; then
echo "$file"
fi
我用bash-x运行了它,这是输出
+ file=file1
++ head -3 file1
++ tr -d '\n'
++ sed 's/\r//g'
+ [[ ASMUTCEDD == [A-Z] ]]
+exit
你错过了什么:
- 您可以使用
检查输入是否只匹配grep
字符(或者正如@Barmar所指出的,Bash的内置正则表达式匹配)[A-Z]
- 您可以在
语句中直接使用管道,而无需if
[…]
file=file1
if head -n 3 "$file" | tr -d '\n\r' | grep -qE '^[A-Z]+$'; then
echo "$file"
fi
要进行正则表达式匹配,必须使用
=~
,而不是=
。正则表达式应该是^[A-Z]*$
。正则表达式匹配字符串中任何位置是否有字母,而不仅仅是字符串是否完全是字母
if [[ $(head -3 $file|tr -d '\n\r') =~ ^[A-Z]*$ ]]; then
echo "$file"
fi
对于此问题,您可以使用内置和:-
#!/bin/bash
file="file1"
C=0
flag=0
while read line
do
(( ++C ))
[ $C -eq 4 ] && break;
[[ "$line" =~ '[^[:alpha:]]' ]] && flag=1
done < "$file"
[ $flag -eq 0 ] && echo "$file"
#/bin/bash
file=“file1”
C=0
标志=0
读行时
做
(++C))
[$C-等式4]&中断;
[[“$line”=~'[^[:alpha:]]]&&flag=1
完成<“$file”
[$flag-eq 0]&回显“$file”
当bash
具有内置正则表达式支持时,为什么要使用grep
呢?@Barmar我可以轻松而自信地编写这篇文章,而无需检查内置正则表达式语法的一些关键细节,例如如何正确引用(如果有),以及+
是否实际工作。简言之,这更容易。另外,要使用[[…]]
,您需要一个子shell。我不是说这是最好的解决方案。这很容易。