我想找到有“abc”和“efg”的文件,这两个字符串在该文件中的不同行。一个包含以下内容的文件:
blah blah..
blah blah..
blah abc blah
blah blah..
blah blah..
blah blah..
blah efg blah blah
blah blah..
blah blah..
应该匹配。
我想找到有“abc”和“efg”的文件,这两个字符串在该文件中的不同行。一个包含以下内容的文件:
blah blah..
blah blah..
blah abc blah
blah blah..
blah blah..
blah blah..
blah efg blah blah
blah blah..
blah blah..
应该匹配。
当前回答
虽然sed选项是最简单、最简单的,但遗憾的是,LJ的一行程序并不是最可移植的。那些受困于C Shell(而不是bash)版本的人将需要摆脱他们的刘海:
sed -e '/abc/,/efg/\!d' [file]
不幸的是,这一行在bash等中不起作用。
其他回答
awk一行程序:
awk '/abc/,/efg/' [file-with-content]
我非常依赖于pcregrep,但是对于更新的grep,您不需要安装它的许多特性。只需使用grep -P。
在OP的问题的例子中,我认为以下选项很好地发挥了作用,第二好的选项符合我对问题的理解:
grep -Pzo "abc(.|\n)*efg" /tmp/tes*
grep -Pzl "abc(.|\n)*efg" /tmp/tes*
我将文本复制为/tmp/test1,删除'g'并保存为/tmp/test2。下面的输出显示,第一个显示匹配的字符串,第二个只显示文件名(典型的-o显示匹配,典型的-l只显示文件名)。请注意,'z'对于多行是必要的,'(.|\n)'意味着匹配'换行符以外的任何内容'或'换行符' -即任何内容:
user@host:~$ grep -Pzo "abc(.|\n)*efg" /tmp/tes*
/tmp/test1:abc blah
blah blah..
blah blah..
blah blah..
blah efg
user@host:~$ grep -Pzl "abc(.|\n)*efg" /tmp/tes*
/tmp/test1
要确定你的版本是否足够新,运行man grep,看看顶部是否出现类似的内容:
-P, --perl-regexp
Interpret PATTERN as a Perl regular expression (PCRE, see
below). This is highly experimental and grep -P may warn of
unimplemented features.
它来自GNU grep 2.10。
我不确定是否可以使用grep,但sed使它非常简单:
sed -e '/abc/,/efg/!d' [file-with-content]
我用它从一个multi fasta文件中提取一个fasta序列,使用grep的-P选项:
grep -Pzo ">tig00000034[^>]+" file.fasta > desired_sequence.fasta
基于perl的搜索 Z表示行以0字节结尾,而不是换行字符 O来捕获匹配的内容,因为grep返回整行(在本例中,因为您做了-z是整个文件)。
regexp的核心是[^>],它翻译为“不大于符号”。
虽然sed选项是最简单、最简单的,但遗憾的是,LJ的一行程序并不是最可移植的。那些受困于C Shell(而不是bash)版本的人将需要摆脱他们的刘海:
sed -e '/abc/,/efg/\!d' [file]
不幸的是,这一行在bash等中不起作用。