Pengelompokan Bahasa Alami – Bagian 1 – Menuju AI – Teknologi, Sains, dan Teknik Terbaik

Penulis: Francesco Fumagalli

Pemrosesan Bahasa Alami

Pengelompokan Bahasa Alami – Bagian 1

Bantu chatbots menangani FAQ, dengan kode Python untuk Tokenisasi, GloVe, dan TF-IDF

Mengklasifikasikan sesuatu menjadi hal yang wajar bagi kami: buku, film, dan musik kami semuanya memiliki genre; hal-hal yang kita pelajari dibagi menjadi beberapa subjek yang berbeda dan bahkan makanan yang kita makan termasuk dalam masakan yang berbeda!
Dalam beberapa tahun terakhir kami telah dapat mengembangkan algoritme yang lebih baik dan lebih baik untuk mengklasifikasikan teks: model seperti BERT-ITPT-FiT (BERT + withIn-Task Pre-Training + Fine-Tuning) atau XL-NET tampaknya menjadi juara bertahan dalam hal ini kategori, setidaknya dalam 29 dataset benchmark yang tersedia di PapersWithCode.

Dalam beberapa tahun terakhir kami telah dapat mengembangkan algoritme yang lebih baik dan lebih baik untuk mengklasifikasikan teks: model seperti BERT-ITPT-FiT (BERT + withIn-Task Pre-Training + Fine-Tuning) atau XL-NET tampaknya menjadi juara bertahan dalam hal ini kategori, setidaknya dalam 29 dataset benchmark yang tersedia di PapersWithCode.

gambar oleh penulis

Tetapi bagaimana jika kita tidak mengetahui kategori yang tersedia untuk teks yang ingin kita analisis? Ambil contoh kumpulan percakapan atau kumpulan buku atau artikel yang semuanya termasuk dalam spesialisasi berbeda dalam subjek yang sama: label tidak selalu sejelas spam / bukan spam, kami mungkin tidak tahu berapa banyak atau apa jenis label yang diharapkan, atau metode klasifikasi normal yang telah dilatih sebelumnya tidak akan memiliki pengetahuan domain mendalam yang diperlukan untuk tidak mengklasifikasikannya sebagai semua sama, sementara tidak tersedia cukup material, waktu, atau daya komputasi untuk menyempurnakan Transformer model.

Mungkin salah satu contoh yang paling jelas adalah mengkategorikan pesan masuk ke dalam FAQ: tidak setiap pesan dapat dijawab melalui FAQ, tetapi kami ingin menghubungkan sebanyak mungkin ke jawaban yang benar, untuk meminimalkan jumlah yang tidak terjawab atau ditangani secara manual , dan secara dinamis meningkatkan FAQ kami dengan menambahkan pertanyaan baru yang menjadi relevan.

Mari kita lihat caranya!

Dari kata-kata menjadi nilai numerik: Tokenisasi dan Penyematan

Hal pertama yang harus kami lakukan, seperti biasa saat berurusan dengan Natural Language, adalah mengubah teks menjadi sesuatu yang dapat dipahami oleh algoritme kami. Paragraf dan kalimat dipecah menjadi komponen dasarnya, kata-kata, dalam proses yang disebut tokenisasi. Tetapi kata-kata itu sendiri tidak dapat diumpankan ke model komputasi karena operasi matematika tidak dapat diterapkan padanya, yang menjelaskan kebutuhan untuk memetakannya ke dalam vektor bilangan real: pada dasarnya diubah menjadi urutan bilangan yang mewakili mereka dalam ruang matematika , juga menjaga hubungan di antara mereka (proses yang dikenal sebagai embedding kata, istilah yang berasal dari matematika untuk mengidentifikasi peta injeksi dan pelestarian struktur).

Kedengarannya rumit, tetapi ada cara sederhana untuk melakukan ini, seperti yang ditunjukkan di bawah ini: mulai dari tiga kalimat (di sebelah kiri) token mereka diekstraksi dan penyematan yang sangat sederhana dilakukan (di sebelah kanan) dengan menghitung kemunculan dari setiap tanda (kata) dalam teks aslinya

Tokenisasi dan Penyematan Vektor Hitung sederhana dari tiga teks pendek.

Dalam contoh di atas, kata startup disematkan sebagai [1,0,1] karena muncul sekali di teks pertama dan ketiga tetapi tidak di teks kedua, sedangkan kata “dalam” disematkan sebagai [0,2,0] karena hanya muncul di kalimat kedua, dua kali.

Perhatikan bahwa ini bukan contoh yang sangat praktis: mengingat jumlah masukan yang sedikit, kata yang berbeda akhirnya memiliki penyematan yang sama (misalnya “khusus” dan “dalam” keduanya hanya muncul di teks kedua, sehingga keduanya berbagi penyematan yang sama [0,1,0]), namun kami berharap ini membantu Anda mendapatkan pemahaman yang lebih baik tentang cara kerja proses tersebut.

Perhatikan juga bahwa semua token adalah huruf kecil dan tanda baca telah dihapus: itu praktik umum, meskipun itu tergantung pada jenis teks yang kita hadapi.

Praktik umum lainnya yang tidak ditampilkan dalam contoh di atas adalah penghapusan stopwords, kata-kata yang sangat umum sehingga tidak relevan dengan tujuan kita dan sangat mungkin ditemukan berkali-kali dalam sebagian besar teks yang kita temukan (seperti “a”, “Yang” atau “adalah”).

Pendekatan ini, bagaimanapun, memberikan keuntungan dari menyematkan dokumen itu sendiri pada saat yang sama dengan kata-kata: membaca tabel secara vertikal, Text1 dapat dibaca sebagai [1,1,1,1,1,1,0,0,0,0]. Ini memudahkan untuk menghadapi sumber yang berbeda dengan memperkenalkan metrik jarak.

Contoh Kode Tokenisasi dengan Python menggunakan nltk:

#! pip install nltk dari nltk.tokenize import word_tokenize text = “Digitiamo adalah Startup dari Italia” tokenized_text = nltk.word_tokenize (teks) print (tokenized_text) # OUTPUT:
# [‘Digitiamo’, ‘is’, ‘a’, ‘Startup’, ‘from’, ‘Italy’]

Contoh Kode Embedding dengan Python menggunakan Word2Vec gensim

#! pip install –upgrade gensim dari gensim.models import Word2Vec
model = Word2Vec ([tokenized_text], min_hitung = 1)
“” “
min_count (int, opsional) – Mengabaikan semua kata dengan frekuensi total lebih rendah dari ini. Word2Vec dioptimalkan untuk bekerja dengan banyak teks sekaligus dalam bentuk daftar teks. Saat bekerja dengan satu teks, teks tersebut harus dimasukkan ke dalam daftar, yang menjelaskan tanda kurung siku di sekitar tokenized_text
“” “print (daftar (model.wv.vocab)) # OUTPUT:
# [‘Digitiamo’, ‘is’, ‘a’, ‘Startup’, ‘from’, ‘Italy’]
Menampilkan embedding untuk sebuah kata. Parameter default Word2Vec menggunakan penyematan 100 dimensi

Embeddings yang umum digunakan: TF-IDF dan GloVe

TF-IDF adalah singkatan dari Term Frequency – Inverse Document Frequency dan ini menekankan pentingnya setiap istilah berdasarkan berapa kali muncul dalam teks lain dari korpus. Ini bisa sangat berguna untuk menyematkan teks dalam domain khusus untuk tujuan pengelompokan. Kata-kata yang muncul di setiap dokumen, tidak peduli seberapa jarang mereka dalam penggunaan sehari-hari, akan diberi bobot yang sangat kecil, sedangkan kata-kata yang hanya muncul di beberapa dokumen akan diberi bobot lebih, sehingga lebih mudah untuk mengenali cluster yang mungkin.
Sebagai contoh, jika kita mencoba menyematkan sekumpulan makalah tentang endokrinologi, kata “endokrinologi” itu sendiri kemungkinan besar akan disebutkan beberapa kali di setiap makalah, sehingga kehadirannya tidak terlalu membantu untuk tujuan membedakannya. GloVe (Vektor Global untuk representasi kata) adalah algoritma tanpa pengawasan yang menghubungkan kata-kata berdasarkan seberapa sering kata-kata itu muncul bersamaan, mencoba memetakan makna yang mendasarinya. Anda dapat melihat beberapa contoh hubungan antara kata-kata yang diperoleh melalui GloVe pada gambar di bawah ini: “pria” kira-kira sama jauhnya dari “wanita” seperti “raja” dari “ratu” yang menuju ke arah yang sama, karena memiliki arti yang sama untuk berbeda jenis kelamin (dan sebaliknya, tentu saja). Hal yang sama terjadi untuk komparatif dan superlatif di panel keempat: vektor yang membawa Anda dari “jelas” ke “lebih jelas”, jika diterapkan ke “lembut”, membawa Anda ke “lebih lembut”.
Bergantung pada ukuran korpus Anda, pustaka Mittens dapat menjadi pelengkap yang baik untuk GloVe: menurut GitHub mereka, “berguna untuk domain yang memerlukan representasi khusus tetapi tidak memiliki cukup data untuk melatihnya dari awal. Sarung tangan dimulai dengan representasi terlatih untuk tujuan umum dan menyesuaikannya ke domain khusus ”, sarung tangan ini juga kompatibel dengan Numpy dan TensorFlow.
(gambar dari sumber resmi GloVe: https://nlp.stanford.edu/projects/glove/)

Luar biasa! Sekarang kita telah mengubah kata-kata kita menjadi vektor numerik dan memetakannya ke dalam spasi, jika kita telah menggunakan embedding yang hanya berfungsi untuk kata-kata dan bukan teks lengkap, inilah waktunya untuk kembali ke kalimat: ingat tujuan awal kita? Kami tidak hanya ingin memetakan kata-kata, tetapi mencoba mengelompokkan teks atau kalimat yang ada di dalamnya.

Ada banyak cara untuk melakukan ini dan beberapa mungkin bekerja lebih baik daripada yang lain, tergantung pada konteksnya. Mungkin cara termudah, yang juga cukup efektif untuk teks pendek, adalah rata-rata penyematan setiap kata dalam teks untuk menghasilkan penyematan seluruh teks.

Untuk materi yang lebih panjang, pendekatan lain adalah mengekstrak kata kunci dan kemudian rata-rata menyematkannya, untuk memastikan rata-rata Anda tidak diencerkan oleh segudang kata umum, tetapi itu memerlukan algoritme ekstraksi kata kunci yang mungkin tidak selalu tersedia.

Contoh Kode Tf-Idf dengan Python menggunakan sklearn

dari sklearn.feature_extraction.text import TfidfVectorizer corpus = [
‘Digitiamo is a Startup from Italy’,
‘Digitiamo is specialized in NLP in Italy’,
‘Italy is not a Startup’
]
vectorizer = TfidfVectorizer () X = vectorizer.fit_transform (corpus) cetak (vectorizer.get_feature_names ())
cetak (bentuk X) # KELUARAN:
# [‘digitiamo’, ‘from’, ‘in’, ‘is’, ‘italy’, ‘nlp’, ‘not’, ‘specialized’, ‘startup’]
# (3, 9) # get_feature_names mengembalikan kamus kata, sedangkan X.shape # adalah 3×9: 3 dokumen, 9 kata berbeda. Kata ‘a’ telah dihentikan.
Model terlatih yang dihasilkan. Kata dicetak terbalik dan dapat dilihat pada daftar get_feature_names di atas, jadi baris pertama (0,4) berarti kata terakhir dari teks pertama, yang merupakan kata kelima (4 + 1, kita hitung dari nol) dalam daftar: “ Italia”. (0,1) adalah “dari”; (0,8) “startup” dan seterusnya.

Menggunakan GloVe dengan Python (sumber)

Setelah Anda mengunduh embedding GloVe dari sumber resminya, Anda dapat menggunakannya seperti yang ditunjukkan di bawah ini (kredit untuk Karishma Malkan)

impor numpy sebagai np

def loadGloveModel (File):
cetak (“Memuat Model Sarung Tangan”)
f = buka (File, ‘r’)
gloveModel = {}
untuk baris di f:
splitLines = line.split ()
kata = splitLines[0]
wordEmbedding = np.array ([float(value) for value in splitLines[1:]])
gloveModel[word] = wordEmbedding
cetak (len (gloveModel), “kata-kata dimuat!”)
kembali gloveModel

Anda kemudian dapat mengakses vektor kata hanya dengan menggunakan variabel gloveModel.

print gloveModel[‘hello’]

Atau, Anda dapat memuat file menggunakan Pandas seperti yang ditunjukkan di bawah ini (kredit untuk Petter)

import panda sebagai pd
import csv words = pd.read_table (glove_data_file, sep = “”, index_col = 0, header = None, quoting = csv.QUOTE_NONE)

Kemudian untuk mendapatkan vektor untuk sebuah kata:

def vec (w):
mengembalikan words.loc[w].as_matrix ()

Dan untuk menemukan kata yang paling dekat dengan vektor:

words_matrix = words.as_matrix ()

def find_closest_word (v):
diff = words_matrix – v
delta = np.sum (diff * diff, axis = 1)
i = np.argmin (delta)
mengembalikan words.iloc[i].nama

File juga dapat dibuka menggunakan gensim seperti yang ditunjukkan di bawah ini (kredit untuk Ben), mungkin metode terbaik karena konsisten dengan metode lain yang pernah kita lihat sebelumnya di artikel ini dan memungkinkan Anda untuk menggunakan metode gensim word2vec (misalnya, kesamaan)

Gunakan glove2word2vec untuk mengonversi vektor GloVe dalam format teks ke dalam format teks word2vec:

dari gensim.scripts.glove2word2vec import glove2word2vec
glove2word2vec (glove_input_file = “vektor.txt”, word2vec_output_file = “gensim_glove_vectors.txt”)

Terakhir, baca word2vec txt ke model gensim menggunakan KeyedVectors:

dari gensim.models.keyedvectors impor KeyedVectors
glove_model = KeyedVectors.load_word2vec_format (“gensim_glove_vectors.txt”, biner = Salah)

Merata-rata embeddings kata untuk mendapatkan embeddings teks

impor kembali
dari gensim.models import Word2Vec text = ‘Digitiamo adalah Startup dari Italia’ tokenized_text = nltk.word_tokenize (teks) model = Word2Vec ([tokenized_text], min_count = 1) modelledText = []
untuk kata dalam teks.split ():
kata = re.sub (r ‘[^ws]’,”,kata)
# hapus tanda baca
modelledText.append (model[word]) embedText = jumlah (modeledText) / len (modeledText)
# Embeddings adalah vektor, sehingga cetakan dapat ditambahkan dan dibagi (embedText)
Vektor tersemat yang dihasilkan (rata-rata) untuk seluruh kalimat

Sekarang setelah kita akhirnya mendapatkan penyematan teks kita, kita dapat mengelompokkannya seolah-olah itu adalah entri data numerik biasa!

Untuk mengetahui lebih lanjut tentang beberapa teknik pengelompokan yang tersedia, baca bagian kedua dari artikel ini, segera tersedia! Jika Anda ingin diberi tahu saat dipublikasikan, berlangganan buletin kami dengan menggeser alat di bawah (seperti membuka kunci iPhone)

https://medium.com/media/1615d33800a6ce8c8c002daa14178fac/href

Dengan memanfaatkan dan menyempurnakan teknik yang dijelaskan dalam artikel ini, kami telah mengembangkan AiKnowYou, produk yang menganalisis dan meningkatkan kinerja chatbot dari waktu ke waktu. Jangan ragu untuk menghubungi kami jika Anda ingin mendapatkan pemahaman yang lebih baik tentang cara kerjanya, atau jika Anda ingin meningkatkan kinerja chatbot Anda sendiri hari ini.

Terima kasih telah membaca!

Kami mengetik logo

Tentang Digitiamo

Digitiamo adalah perusahaan rintisan dari Italia yang berfokus pada penggunaan AI untuk membantu perusahaan mengelola dan memanfaatkan pengetahuan mereka. Untuk mengetahui lebih lanjut, kunjungi kami.

Tentang Penulis

Fabio Chiusano adalah Kepala Ilmu Data di Digitiamo; Francesco Fumagalli adalah ilmuwan data yang bercita-cita tinggi melakukan magang R&D.

Pengelompokan Bahasa Alami – Bagian 1 awalnya diterbitkan di Towards AI on Medium, di mana orang-orang melanjutkan percakapan dengan menyoroti dan menanggapi cerita ini.

Diterbitkan melalui Towards AI