bashスクリプトがファイル名を他のエンコーディングの特殊文字と一致させるように強制します。

bashスクリプトがファイル名を他のエンコーディングの特殊文字と一致させるように強制します。

別の場所のファイル名を比較するbashスクリプトがあります。ファイル名には2つの異なるエンコーディングの特殊文字があるため、私のスクリプトはその特定のファイルと一致しません。

Bashを一致させる方法はありますか?

これはそれぞれutf8とTIS-620のサンプルファイル名でエンコードされていますLöfflerLöffler

スクリプトの例:

for i in /dir1/*; do
if [ ! -h "$i" ]; then
[ -d "/dir2/${i##*/}" ]
fi

使用ウナム次の情報を入手できます。

ö utf8バージョン

Octal  Decimal      Hex        HTML    Character   Unicode
0366      246     0xF6      ö    "ö"         LATIN SMALL LETTER O WITH DIAERESIS

TIS-620バージョンö

Octal  Decimal      Hex        HTML    Character   Unicode
0157      111     0x6F      o    "o"         LATIN SMALL LETTER O
01410      776    0x308      ̈    "̈"         COMBINING DIAERESIS

編集する:

矛盾を引き起こす最初の原因は、UTF正規化を使用するツールでした。異なるエンコーディングで同じ文字を一致させる方法を知りたいです。つまり、BASHスクリプトでUTF正規化インラインをどのように使用しますか?

ベストアンサー1

エンコーディングでいくつかの「テキスト」を比較する必要があると思います。TIS-620のコードページ(タイ語)〜utf8エンコーディング(ユニバーサル)同等。

さて、最も一般的なエンコーディング(UTF-32と同じくらい多くの文字をエンコードする)はutf8なので、最も基本的なエンコーディングであるTIS-620をutf8に変換する必要があります。

一般的に使用されるエンコーディング変換ツールは次のとおりです。iconv。このツールを使用すると、次のことができます。

$ printf '\xC1' | iconv -f TIS620 -t utf8

端末がutf8を許可している場合は、ม文字を確認してください。この役割の値はC1WikipediaのTIS-620表にあります。

または、文字を構成するバイトを「参照」(utf8形式):

$ printf '\xC1' | iconv -f TIS620 -t utf8 | od -vAn -tx1
e0 b8 a1

Unicodeコードポイント番号を使用して文字をエンコードするときに生成される3バイトは何ですか?U0E21 ファイル形式からそれとも、ウェブサイト: www.utf8-chartable.de:

U+0E21  ม   e0 b8 a1    THAI CHARACTER MO MA

iconvでTIS620で使用できるエンコーディングのリストは次のとおりです。

$ iconv -l | grep 620
TIS-620//
TIS620-0//
TIS620.2529-1//
TIS620.2533-0//
TIS620//

ファイル名のエンコードと一致するものを選択してください。


しかし、見つかりません。ウムラウトöタイ語。
これタイ TIS620 ページ または(非常に古い)ISO/IEC 10646-1:1993へのタイ語翻訳タイ語にウムラウトoがあることを表示しないでください。

質問を再編集できますか?


コレクションについて

コンソール/ターミナルがutf8を理解するように構成されているとします。そして、ディレクトリに異なる発音区別記号を使用して3つのファイル名を作成しましょう。

  1. ラテン語 ö (Unicode コードポイント) (utf8 で 0xC3 0xB6 で表される)。
    分音記号付きラテン小文字 O(U+00F6)
    ラテン脳

    $ printf 'L\xC3\xB6ffler'; echo
    Löffler
    
  2. ラテン語 ö (文字 o の後に区切り記号が続く) (utf8 では 0x6F 0xCC 0x88)。
    結合部分法(U+0308)
    部分的なトーン

    $ printf 'Lo\xCC\x88ffler'; echo
    Löffler
    
  3. と:分音記号付きのキリル文字o(utf-8では0xD3 0xA7)
    分音記号付きのキリル小文字O(U+04E7)
    分音符付きのキリル文字O

    $ printf 'L\xD3\xA7ffler'; echo
    Lӧffler
    

これらのファイル名で3つのファイルを作成するには、次のようにします。

$ touch $(printf 'L\xC3\xB6ffler Lo\xCC\x88ffler L\xD3\xA7ffler')

これらのファイルを一覧表示する1つの方法は、一致するglob(対応するファイルのみ)を使用することです。
この場合、fflerすべてのファイルに末尾が表示されます。

$ echo *ffler
Löffler Löffler Lӧffler

このエコーの結果は、次のように詳細に表示できます。

$ echo *ffler | od -vAn -tx1c
  4c  6f  cc  88  66  66  6c  65  72  20  4c  c3  b6  66  66  6c
   L   o 314 210   f   f   l   e   r       L 303 266   f   f   l
  65  72  20  4c  d3  a7  66  66  6c  65  72  0a
   e   r       L 323 247   f   f   l   e   r  \n

これは、誰もが違うという事実を反映しています。

シェルの位置パラメータに割り当てられている場合:

$ set -- $(echo *ffler)

各項目を比較できます。

[ "$1" == "$2" ] && echo "Diferent" || echo "Equal"

しかし、最初と2番目が同じであると予想するのは合理的です。
しかし違いは「構成」を完成する方法。 NFC(統合)形式を
使用します。 NFD(分解)形式を使用します。'L\xC3\xB6ffler'
'Lo\xCC\x88ffler'

uconv(icu-devtoolsパッケージから)これら2つの形式の間を変換します。
分解されたモード:

$ echo *ffler | uconv -x any-nfd | od -vAn -tx1c
  4c  6f  cc  88  66  66  6c  65  72  20  4c  6f  cc  88  66  66
   L   o 314 210   f   f   l   e   r       L   o 314 210   f   f
  6c  65  72  20  4c  d0  be  cc  88  66  66  6c  65  72  0a
   l   e   r       L 320 276 314 210   f   f   l   e   r  \n

事前組み立てられたモード:

$  echo *ffler | uconv -x any-nfc | od -vAn -tx1c
  4c  c3  b6  66  66  6c  65  72  20  4c  c3  b6  66  66  6c  65
   L 303 266   f   f   l   e   r       L 303 266   f   f   l   e
  72  20  4c  d3  a7  66  66  6c  65  72  0a
   r       L 323 247   f   f   l   e   r  \n

この値を位置パラメータに設定して比較すると、次のようになります。

$ set -- $( echo *ffler | uconv -x any-nfc | od -vAn -tx1c )
$ [ "$1" == "$2" ] && echo "Diferent" || echo "Equal"

キリル文字はそのような構成形式と同義ではありません。
名前を他の名前と比較できるように変換する必要がある場合は、マルチバイト文字を理解するためのツールが必要です。

$ echo *ffler | sed 's/\xd3\xa7/\xc3\xb6/g' | od -vAn -tx1c
  4c  6f  cc  88  66  66  6c  65  72  20  4c  c3  b6  66  66  6c
   L   o 314 210   f   f   l   e   r       L 303 266   f   f   l
  65  72  20  4c  c3  b6  66  66  6c  65  72  0a
   e   r       L 303 266   f   f   l   e   r  \n

NFC形式でのみ機能します。

$ echo *ffler | uconv -x any-nfc | sed 's/\xd3\xa7/\xc3\xb6/g' | od -vAn -tx1c
  4c  c3  b6  66  66  6c  65  72  20  4c  c3  b6  66  66  6c  65
   L 303 266   f   f   l   e   r       L 303 266   f   f   l   e
  72  20  4c  c3  b6  66  66  6c  65  72  0a
   r       L 303 266   f   f   l   e   r  \n

今、3つの名前はまったく同じです。

上記の内容で、あなたの実際の懸念が明確になりましたか?
まだ近いですか?

おすすめ記事