正则表达式字符恰好出现x次

时间:2016-11-14 20:13:21

标签: regex linux bash grep

我在bash工作,我有一个大文件,我想要删除所有与某个正则表达式不匹配的行,可能使用$ grep -e "<regex>" <file> > output.txt

我想保留的是任何包含 x 次指定字符的行,例如二进制序列

  <00> 0000,0001,0010,0011,0100,0101,0111,1000,1001,1010,1011,1100,1101,1110,1111

我想只保留那些有2 1 的人,留下我

  

0011,0101,0110,1001,1010,1100

然后我会使用一个bash变量来改变我需要的数量(总是恰好是长度的一半,使用相同长度的字符串) 我偶尔会找到一半 0 和一半 1

的行

我现在有这个。它没有使用正则表达式。它有效,但速度很慢:

$1是每个字符串的长度,$d只是一个目录)

sed -e 's/\(.\)/\1 /g' < $d/input.txt > $d/spaces.txt
awk '{c=0;for(i=1;i<=NF;++i){c+=$i};print c}' $d/spaces.txt > $d/sums.txt
grep -n "$(($1/2))" $d/sums.txt | cut -f1 -d: > $d/linenums.txt
for i in $(cat $d/linenums.txt)
do
    sed "${i}q;d" $d/input.txt 
done > $d/valids.txt

如果你想知道这会在1010转换为1 0 1 0的每个数字之间放置空格,那么它会将值加在一起,将结果保存在sums.txt中,将grep保存为长度/ 2并仅保存在linenums.txt中的行号,然后它读取linenums.txt并从input.txt输出相应的行到output.txt

我需要更快的东西,for循环是太长时间了

感谢您的时间并与我分享您的知识。

1 个答案:

答案 0 :(得分:2)

你绝对可以加快速度。

这是一个grep正则表达式示例,用于匹配恰好两次出现1的任何行:

grep '^\([^1]*1[^1]*\)\{2\}$' input.txt

您可以对此进行概括,以恰好匹配n c次出现的grep "^\([^$c]*$c[^$c]*\)\{$n\}\$" input.txt

0

你还提到想要匹配一半1 s,一半awk s的行。由于您规定所有行的长度相同,因此您只能考虑第一行,并使用wc(或n)获取行长并选择n=`head -n1 input.txt | awk '{printf "%d\n",length($0)/2}'` c=1 grep "^\([^$c]*$c[^$c]*\)\{$n\}\$" input.txt

{{1}}