GNU/Linux >> Belajar Linux >  >> Linux

Menggunakan Uniq Pada Teks Unicode?

Saya ingin menghapus baris duplikat dari file dengan kata-kata skrip Syria. File sumber memiliki 3 baris, baris pertama dan ketiga identik.

$ cat file.txt 
ܐܒܘܢ
ܢܗܘܐ
ܐܒܘܢ

Saat saya menggunakan sort dan uniq , hasilnya menganggap bahwa semua 3 baris identik, yang salah:

$ cat file.txt | sort | uniq -c
      3 ܐܒܘܢ

Menyetel lokal secara eksplisit ke bahasa Suryani juga tidak membantu.

$ LC_COLLATE=syr_SY.utf8 cat file.txt | sort | uniq -c      
     3 ܐܒܘܢ

Mengapa itu bisa terjadi?
Saya menggunakan Kubuntu 18 dan bash, jika itu penting.

Jawaban yang Diterima:

Implementasi GNU dari uniq seperti yang ditemukan di Ubuntu, dengan -c , tidak melaporkan jumlah identik yang bersebelahan garis tetapi jumlah garis yang berdekatan yang mengurutkan sama¹.

Sebagian besar lokal internasional pada sistem GNU memiliki bug bahwa banyak karakter yang sama sekali tidak terkait telah didefinisikan dengan urutan pengurutan yang sama sebagian besar karena urutan pengurutannya tidak ditentukan sama sekali. Sebagian besar OS lain memastikan semua karakter memiliki urutan penyortiran yang berbeda.

$ expr ܐ = ܒ
1

(expr = operator, untuk argumen yang bukan numerik, mengembalikan 1 jika operan mengurutkan yang sama, 0 jika tidak).

Itu sama dengan ar_SY.UTF-8 atau en_GB.UTF-8 .

Yang Anda perlukan adalah lokasi di mana karakter-karakter itu diberi urutan penyortiran yang berbeda. Jika Ubuntu memiliki lokal untuk bahasa Syria, Anda dapat mengharapkan karakter tersebut diberi urutan penyortiran yang berbeda, tetapi Ubuntu tidak memiliki lokal tersebut.

Anda dapat melihat output dari locale -a untuk daftar lokal yang didukung. Anda dapat mengaktifkan lebih banyak lokal dengan menjalankan dpkg-reconfigure locales sebagai root . Anda juga dapat menentukan lebih banyak lokal secara manual menggunakan localedef berdasarkan file definisi di /usr/share/i18n/locales , tetapi Anda tidak akan menemukan data untuk bahasa Syria di sana.

Perhatikan bahwa di:

LC_COLLATE=syr_SY.utf8 cat file.txt | sort | uniq -c

Anda hanya menyetel variabel LC_COLLATE untuk cat perintah (yang tidak memengaruhi cara mengeluarkan konten file, cat tidak peduli tentang pemeriksaan atau bahkan pengkodean karakter karena ini bukan utilitas teks). Anda ingin mengaturnya untuk keduanya sort dan uniq . Anda juga ingin menyetel LC_CTYPE ke lokal yang memiliki rangkaian karakter UTF-8.

Karena sistem Anda tidak memiliki syr_SY.utf8 lokal, itu sama dengan menggunakan C lokal (lokal default).

Sebenarnya, di sini lokal C atau C.UTF-8 mungkin adalah lokal yang ingin Anda gunakan.

Di lokal tersebut, urutan susunan didasarkan pada titik kode, titik kode Unicode untuk C.UTF-8, nilai byte untuk C, tetapi pada akhirnya sama dengan pengkodean karakter UTF-8 yang memiliki properti itu.

$ LC_ALL=C expr ܐ = ܒ
0
$ LC_ALL=C.UTF-8 expr ܐ = ܒ
0

Jadi dengan:

(export LANG=ar_SY.UTF-8 LC_COLLATE=C.UTF-8 LANGUAGE=syr:ar:en
 unset LC_ALL
 sort <file | uniq -c)

Anda akan memiliki LC_CTYPE dengan UTF-8 sebagai rangkaian karakter, urutan susunan berdasarkan titik kode, dan pengaturan lain yang relevan dengan wilayah Anda, jadi misalnya pesan kesalahan dalam bahasa Syria atau Arab jika GNU coreutils sort atau uniq pesan telah diterjemahkan dalam bahasa tersebut (belum ada).

Terkait:Bagaimana cara menandai beberapa kontak untuk mengirim teks yang sama dengan bcc – fitur yang ada di Android?

Jika Anda tidak peduli dengan lainnya itu pengaturan, sama mudahnya (dan juga lebih portabel) untuk digunakan:

<file LC_ALL=C sort | LC_ALL=C uniq -c

Atau

(export LC_ALL=C; <file sort | uniq -c)

seperti yang telah ditunjukkan oleh @isaac.


Linux
  1. urutkan Contoh Perintah di Linux

  2. urutkan:perintah tidak ditemukan

  3. Cara menghapus kata duplikat dari file teks biasa menggunakan perintah linux

  1. Menambahkan Teks Di Akhir File Teks?

  2. Bagaimana cara menghitung jumlah nilai unik suatu bidang dalam file teks yang dibatasi tab?

  3. Menggunakan nc untuk mentransfer file besar

  1. Urutkan Bagian Dari File?

  2. Buat file dengan menggunakan baris perintah di Linux

  3. Menyortir file yang dibatasi tab