0

如果我有如下文件:

cat file1.txt
foo
bar
cat file2.txt
foo
baz
cat file3.txt
bar
baz

是否有关于 ripgrep(或类似)的命令将搜索例如包含 foo 和 bar 的文件?例如,它会显示 file1.txt 而不是其他两个文件?(注意 foo 和 bar 可能不在同一行。)

然后第二个问题,为了更花哨,我可以使用一些语法来计算带有 foo 的文件,但如果它们也包含 bar,则排除它们?所以例如它只会显示file2.txt?

谢谢!

4

1 回答 1

0

RipGrep 默认使用Rust RegEx crate。它非常好,但仍然缺少一些功能,即前瞻和后向引用。RipGrep 还支持PCRE2,它确实具有前瞻和后向引用,但必须专门编译(必须安装Rust 。)

$ cargo build --release --features 'pcre2'

关于在文件中搜索可能由换行符分隔的文本,默认 ripgrep 提供了一个多行选项:

$ rg multiline 'foo.*bar' # can be shortened to -U

但是,.字符类型匹配除换行符以外的任何内容,因此必须专门匹配它们:

$ rg -U 'foo.*[\n\r]*.*bar' *.txt # troublesome...

这在涉及多行时会出现问题,因此另一种技术是使用一个选项来告诉.也匹配换行符:

$ rg -U --multiline-dotall 'foo.*bar' *.txt

或使用选项设置来告诉.也匹配换行符:

$ rg -U '(?s)foo.*bar' *.txt

结果:

$ echo -e 'foo\nbar' > file1.txt
$ echo -e 'foo\nbaz' > file2.txt
$ echo -e 'bar\nbaz' > file3.txt

$ rg -U '(?s)foo.*bar' file*.txt
file1.txt
1:foo
2:bar

为了找到所有带有 'foo' 而不是 'bar' 的文件,有必要使用look-ahead,或者更具体地说,使用负前瞻。只有编译了 PCRE2 支持的 RipGrep 才能工作:

$ rg -U --pcre2 '(?s)foo.*^(?!.*bar)'
file2.txt
1:foo
于 2022-01-28T19:45:40.560 回答