フィールドの区切り記号を置き換える

フィールドの区切り記号を置き換える

フィールドが.で区切られたCSVがあります|

|time: 10:19 | Error: File not found| Condition: None | path: some 

|time: 10:20 | Error: File not found| Condition: a|b | path: some

区切り文字は|時々4番目のフィールド(フィールドCondition)に表示されます。私はそれを|次に変更したいと思いますOR

Condition: a|bになります: Condition: a OR b

これを達成するためにsedまたはawkをどのように使用できますか?

答え1

awk -F'|' -v OFS='|' 'NF == 6 {$4 = $4 " OR " $5; $5=$6; NF--} 1' file

これはパイプで区切られたフィールドでのみ機能します。 5つが予想されますが、もう1つがある場合は、必要な文字列にリンクしてください。

またはGNU sed:

sed 's/|/|/5; ta; n; :a; s/|/ OR /4' file

チューブが5本ある場合は、4番目のチューブを交換してください。 MacOSでは、デフォルトのsedでは機能しません。 MacOS sedは、セミコロンが改行文字に置き換えられている場合に使用できます(BSD派生sedの場合は、ラベル名の後に改行文字が続く必要があるようです)。


あればどうでしょうか?もっと追加のパイプは1つ以上ですか?次の記事を検討してください。

|time: 10:19 | Error: File not found| Condition: None | path: some
|time: 10:20 | Error: File not found| Condition: a|b | path: someh
|time: 12:34 | NO ERROR | Condition: a|b AND c|d AND e|f | path: nil

sedを拡張する解決策は簡単です。 「jump-if」を追加するだけです。

sed ':b; s/|/|/5; ta; n; :a; s/|/ OR /4; tb' file

awkは少し冗長になります。

awk -F'|' -v O FS='|' '{
    while (NF > 5) {
        $4 = $4 " OR " $5
        for (i = 5; i < NF; i++)
            $i = $(i+1)
        NF--
    }
    print
}' file

答え2

これをテストしてみてください。

sed 's/Condition:[ ]*\([a-zA-Z]*\)|\([a-zA-Z]*\)/Condition: \1 OR \2/g' your_file

aそれを仮定してb文字です。

答え3

Python3スクリプト。 csvファイルを区切り文字「|」で定義されたリストに分割し、追加のフィールドがあり、「condition:」という単語で始まる場合は、そのフィールドを結合します。

import csv

for line in list(csv.reader(open('filename', 'r'), delimiter='|')):
    if len(line) > 5 and line[3].lstrip().startswith('Condition:'):
        print('|'.join(line[:3] + [line[3] + ' OR ' + line[4]]+line[5:]))
    else:
        print('|'.join(line))

答え4

コード例では、ルールが定義|されている場所ごとに表示されます。いいえ両側にスペースがあるのでORとてもシンプルにしたいです。

sed -E 's/([^ ])\|([^ ])/\1 OR \2/g' test

関連情報