編集する:とても複雑にしました。これはリバース grep とは関係ありません。ただ使用しても同じ結果が得られますgrep -x -f stop.txt < in.txt
。不用語ファイルのwho
前にある場合、whose
結果はですwho
。不用語ファイルの順序が変わるin.txt
と、2行が見つかります。 grepを全く理解していないようです。
ファイルから不用語を含む行を削除するのと同じように、逆方向grepを機能させることはできません。不用語が提供される順序は結果に影響を与えます。
2つのファイルがあるとしましょう。入力ファイルin.txt
:
who
whose
そして、不用語のリストを含むファイルは次のとおりですstop.txt
。
who
whose
in.txt
逆grep検索を使用しての停止単語を「フィルタリング」すると、次のような結果がstop.txt
得られます。
$ grep -vx -f stop.txt < in.txt
whose
$
stop.txt
私が次に変更した場合のみ
whose
who
私は得る:
$ grep -vx -f stop.txt < in.txt
$
不用語を含むファイルの単語の順序がなぜ重要なのかわかりません。
答え1
スキーマファイルを含める
$ od -bc shortlong
0000000 167 150 157 012 167 150 157 163 145 012
w h o \n w h o s e \n
0000012
$ od -bc longshort
0000000 167 150 157 163 145 012 167 150 157 012
w h o s e \n w h o \n
0000012
grep
macOS(2.5.1-FreeBSD)を使用していくつかの変更をテストできます。
$ grep -x -f shortlong shortlong
who
$ grep -x -f shortlong longshort
who
$ grep -x -f longshort shortlong
who
whose
$ grep -x -f longshort longshort
whose
who
who
最初の項目が長いwhose
一致を隠すとき。これはバグのようです。
問題は、式がファイルから出てくるときにのみ発生-f
し、同等の(希望する)式が引数として提供されるときには発生しません。
$ grep -x -E 'who|whose' shortlong
who
whose
$ grep -x -E 'who|whose' longshort
whose
who
$ grep -x -E 'whose|who' shortlong
who
whose
$ grep -x -E 'whose|who' longshort
whose
who
GNU grep
(3.7)にはこの問題はありません(grep
現在のバージョンのOpenBSDも同様です):
$ ggrep -x -f shortlong shortlong
who
whose
$ ggrep -x -f shortlong longshort
whose
who
$ ggrep -x -f longshort shortlong
who
whose
$ ggrep -x -f longshort longshort
whose
who
したがって、このエラーを回避するには、バージョン2.5.1-FreeBSDを使用しないか、grep
非端末値をforパラメータに置き換えてファイルに正規表現を設定します。\n
|
grep -E
$ paste -s -d \| shortlong
who|whose
$ grep -x -E -- "$(paste -s -d \| shortlong)" shortlong
who
whose
シフトについて
理想的には、正規表現の置換では、長い文字列を短い文字列の前にリストする必要があります。他の極端なケースの中でこれは、人々がlongshort
ファイルやwhose|who
テーブルを好む必要があることを意味します。
grep
(エラーがない場合)正しい結果を得るために表示されますが、他の正規表現エンジンは最初の一致で停止するため、一致させるには最長の一致を最初にリストする必要があります。
$ printf 'who whoses the whosefolk' |
grep -o -E 'who|whose|whosefolk'
who
whose
whosefolk
$ printf 'who whoses the whosefolk' |
perl -nle 'print for /who|whose|whosefolk/g'
who
who
who
$ printf 'who whoses the whosefolk' |
perl -nle 'print for /whosefolk|whose|who/g'
who
whose
whosefolk