Unix ツールを使用して 2 つの文字列のトークンの違いを見つけるにはどうすればよいでしょうか?

Unix ツールを使用して 2 つの文字列のトークンの違いを見つけるにはどうすればよいでしょうか?

以下のような2つの文字列があります。

token1, token2, token3, token4, token5, token6, token8, token9, token10

token2, token7, token4, token3, token5, token6, token8, token10, token9

token1視覚的には、 やのような「トークン」が両方の文字列に存在しないことがわかりますtoken7。しかし、Unix ツールを使用して異なるトークンを取得する簡単な方法はありますか?

長いルートは、スクリプトを書いて、{token => count} のハッシュマップを維持し、最終的に count = 1 のキーのみを出力することです。しかし、もっと短い方法があると思います。

答え1

GNU: について:

s1='token1, token2, token3, token4, token5, token6, token8, token9, token10'
s2='token2, token7, token4, token3, token5, token6, token8, token10, token9'
comm <(grep -oE '\w+' <<< "$s1" | sort) <(grep -oE '\w+' <<< "$s2" | sort)

与えるもの:

token1
                token10
                token2
                token3
                token4
                token5
                token6
        token7
                token8
                token9

列は次のとおりです。

  1. トークンはS1のみ
  2. トークンはS2のみ
  3. 両方のトークン。

対応するオプションを渡すことで列を抑制します (たとえば、-33 番目の列を抑制する)。

答え2

ラメシュから基本的な考え方を盗む

GNUawkではbash

awk -v RS='[[:space:]]*,[[:space:]]*' '{x[$0]++}; END{for (y in x) if (x[y] == 1) print y}'  
<(printf "%s" 'token1, token2, token3, token4, token5, token6, token8, token9, token10')  
<(printf "%s" 'token2, token7, token4, token3, token5, token6, token8, token10, token9')
token1
token7

答え3

以下のようなことができます。

cat input1 input2 >> output
arr=$(cat output | tr "," "\n")
echo "${arr[@]}" | tr ' ' '\n' | sort -u | tr '\n' ' '

説明

2 つのファイルを別のファイルに結合し、トークンをコンマで区切って分割しています。その後、一意の値のみを出力します (つまり、1 回だけ発生する値のみで、これが探しているものだと思います)。

input1ファイルの内容

token1, token2, token3, token4, token5, token6, token8, token9, token10

input2ファイルの内容

token2, token7, token4, token3, token5, token6, token8, token10, token9

上記のスクリプトを実行すると、次のような出力が得られます。

token1 token10 token2 token3 token4 token5 token6 token7 token8 token9

上記の出力を見ると、両方のファイルからの一意の値のみが印刷されていることがわかります。

ただし、差分だけが必要な場合は、以下のコマンドを使用できます。

echo ${arr[@]} | sort | uniq -c

関連情報