入力ファイルがあり、段落内で別の一致を検索し、一致がある場合は、段落全体を含む出力ファイルに移動する必要があります。
1つの重要な点は、出力順序が入力順序を反映する必要があることです。だから段落を検索する必要があります。みんなパターンマッチングファイルのパターン(1行に1つのパターン)、そして一つパターンの一致 該当する段落の追加一致を停止し、一致する段落を出力ファイルに移動し、次の段落に処理をスキップします。
入力ファイル:
DFJKHDKQW
YYYYYYYYYYYY
SDFLKJHSDKLFH
DSFLKHSDLKFH
DFIHERFW
ADFKJH
OIGHRFGH
XXXXXXXXXXXX
SDKFLJH
DFLKHSDFKLH
SDSDJKLFHSDK
OIHGSDFG
AAAAAAAA
LFKHFGJKDGH
KLJHLUG
DFSDKLF
YYYYYYYYYYYY
パターンマッチファイル:
AAAAAAAA
YYYYYYYYYYYY
XXXXXXXXXXXX
予想出力:
DFJKHDKQW
YYYYYYYYYYYY
SDFLKJHSDKLFH
DSFLKHSDLKFH
DFIHERFW
ADFKJH
OIGHRFGH
XXXXXXXXXXXX
SDKFLJH
OIHGSDFG
AAAAAAAA
LFKHFGJKDGH
KLJHLUG
DFSDKLF
YYYYYYYYYYYY
awk
私は今想像を超えた一連の問題に直面しています。
- 入力ファイルを使用したパターンの一致
- 最初に表示されたときに段落を回転し、「次の段落に停止/ジャンプ」
- 一致する段落を出力ファイルにコピーします。
- 入力から一致する段落を削除します(
diff
後で2つのファイル間でこれを行うことができるので、オプション)。
答え1
完全な行文字列の一致を実行すると仮定すると、次のものが必要です。
$ cat tst.awk
BEGIN {
ORS = "\n\n"
FS = "\n"
}
NR==FNR {
tgts[$0]
next
}
{
out = "unmatched"
for (i=1; i<=NF; i++) {
if ($i in tgts) {
out = "matched"
break
}
}
print > out
}
$ awk -f tst.awk targets RS= file
$ ls *matched
matched unmatched
$ head -100 *matched
==> matched <==
DFJKHDKQW
YYYYYYYYYYYY
SDFLKJHSDKLFH
DSFLKHSDLKFH
DFIHERFW
ADFKJH
OIGHRFGH
XXXXXXXXXXXX
SDKFLJH
OIHGSDFG
AAAAAAAA
LFKHFGJKDGH
KLJHLUG
DFSDKLF
YYYYYYYYYYYY
==> unmatched <==
DFLKHSDFKLH
SDSDJKLFHSDK
文字列一致ではなく正規表現を実行する必要がある場合、または正確に一致するのではなく部分を実行する必要がある場合は、別の解決策が必要です(そして、要件をよりよく説明するために質問を更新してください)。
答え2
パターンマッチmatch
それぞれを1つの別々のパターンで入力してください。infile
入力してみてください:
awk -F'\n' '!input && !matches[$0]{ next; };
{ for(i=1; i<=NF; i++) {
if($i in matches) { print sep $0; sep=ORS; break; };
};
}' match input=1 RS= infile
またはパターンマッチングmatch
パターンブロックを入力してください。infile
入力(同じブロックを追加します。match
入力infile
確認するために)以下を試してください。
awk -v RS= '!input && !matches[$0]{ next; }; ($0 in matches)' match input=1 infile
答え3
短絡モードが既にわかっているので、次のように動作します。まず、「スキーマ」ファイルを解析してから、実際の入力を解析します。出力は通常どおりコンソールに印刷されますが、もちろんファイルにリダイレクトすることもできます。
awk -v ORS="\n\n" 'NR==FNR{pat[++npat]=$0;next}
{for (i=1;i<=npat;i++) {if (index($0,pat[i])) {print;next}}}' patterns.txt RS="" input.txt
これは、最初に出力レコード区切り文字を2つの改行に設定し、印刷された段落が入力のように空白行に区切られるようにします。
最初のファイルを処理するとき(
FNR
ファイルごとのラインカウンタがNR
グローバルラインカウンタと同じ)、すべてのパターンを配列変数に保存するだけですpat
。2番目のファイルの場合、レコード区切り文字は空白に設定されており、これは
awk
「ショートモード」で実行されていることを示します。その後、すべてのパターンを繰り返し、関数を介してindex()
入力レコードにそのパターンが見つかったかどうかを明示的に確認します。
ノート
この解決策は「部分文字列マッチング」を実行します。言い換えれば、行の1つにある種の「パターン」が見つかった場合、その段落は一致すると見なされます。
この
index()
機能は、以下を保証するために使用されます。言葉「検索パターン」に正規表現に固有の文字が含まれている場合でも、文字列は一致します。実際に正規表現の一致を使用するには、代わりif ($0 ~ pat[i])
にそれを使用してください。