Version 2020 de 100 coups de traitement du langage, qui est célèbre comme une collection de problèmes de traitement du langage naturel, a été publié. Cet article résume les résultats de la résolution du «Chapitre 7: Vecteurs de mots» des chapitres 1 à 10 ci-dessous.
Nous utilisons Google Colaboratory pour obtenir des réponses. Pour plus d'informations sur la configuration et l'utilisation de Google Colaboratory, consultez cet article. Le cahier contenant les résultats d'exécution des réponses suivantes est disponible sur github.
Créez un programme qui exécute le traitement suivant pour un vecteur de mot (incorporation de mots) qui exprime la signification d'un mot en tant que vecteur réel.
Téléchargez le vecteur de mots appris (3 millions de mots / phrases, 300 dimensions) dans le jeu de données de Google Actualités (environ 100 milliards de mots) et affichez le vecteur de mots «États-Unis». Cependant, notez que "États-Unis" est appelé en interne "États-Unis".
Tout d'abord, téléchargez le vecteur de mot appris spécifié.
FILE_ID = "0B7XkCwpI5KDYNlNUTTlSS21pQmM"
FILE_NAME = "GoogleNews-vectors-negative300.bin.gz"
!wget --load-cookies /tmp/cookies.txt "https://docs.google.com/uc?export=download&confirm=$(wget --quiet --save-cookies /tmp/cookies.txt --keep-session-cookies --no-check-certificate 'https://docs.google.com/uc?export=download&id=$FILE_ID' -O- | sed -rn 's/.*confirm=([0-9A-Za-z_]+).*/\1\n/p')&id=$FILE_ID" -O $FILE_NAME && rm -rf /tmp/cookies.txt
Il lit ensuite le mot vecteur en utilisant Gensim, qui est utilisé dans diverses tâches de traitement du langage naturel.
from gensim.models import KeyedVectors
model = KeyedVectors.load_word2vec_format('./GoogleNews-vectors-negative300.bin.gz', binary=True)
Après la lecture, vous pouvez facilement obtenir un vecteur de mot simplement en spécifiant le mot que vous souhaitez vectoriser.
model['United_States']
production
array([-3.61328125e-02, -4.83398438e-02, 2.35351562e-01, 1.74804688e-01,
-1.46484375e-01, -7.42187500e-02, -1.01562500e-01, -7.71484375e-02,
1.09375000e-01, -5.71289062e-02, -1.48437500e-01, -6.00585938e-02,
1.74804688e-01, -7.71484375e-02, 2.58789062e-02, -7.66601562e-02,
-3.80859375e-02, 1.35742188e-01, 3.75976562e-02, -4.19921875e-02,
・ ・ ・
Calculez la similitude cosinus entre «États-Unis» et «États-Unis».
Ici, la méthode de la `` similarité '' est utilisée. Si vous spécifiez deux mots, vous pouvez calculer la similitude cosinus entre les mots.
model.similarity('United_States', 'U.S.')
production
0.73107743
Sortie de 10 mots avec une forte similitude cosinus avec "États-Unis" et leur similitude.
Ici, la méthode la plus_similaire '' est utilisée. Si vous spécifiez un mot, vous pouvez obtenir les meilleurs mots de similitude jusqu'à
topn '' et leur similitude.
model.most_similar('United_States', topn=10)
production
[('Unites_States', 0.7877248525619507),
('Untied_States', 0.7541370391845703),
('United_Sates', 0.74007248878479),
('U.S.', 0.7310774326324463),
('theUnited_States', 0.6404393911361694),
('America', 0.6178410053253174),
('UnitedStates', 0.6167312264442444),
('Europe', 0.6132988929748535),
('countries', 0.6044804453849792),
('Canada', 0.6019070148468018)]
Soustrayez le vecteur "Madrid" du vecteur de mots "Espagne", calculez le vecteur en ajoutant le vecteur "Athènes" et produisez 10 mots avec une grande similitude avec ce vecteur et leur similitude.
La méthode la plus_similaire '' utilisée dans la question précédente vous permet de spécifier le vecteur d'addition et le vecteur de soustraction, respectivement, puis d'obtenir des mots qui ont un degré élevé de similitude avec le vecteur calculé. Ici, en suivant les instructions de l'énoncé du problème, nous affichons des mots très similaires au vecteur de
Espagne```-
Madrid+
Athens``` La `` Grèce '' est à la première place.
vec = model['Spain'] - model['madrid'] + model['Athens']
model.most_similar(positive=['Spain', 'Athens'], negative=['Madrid'], topn=10)
production
[('Greece', 0.6898481249809265),
('Aristeidis_Grigoriadis', 0.5606848001480103),
('Ioannis_Drymonakos', 0.5552908778190613),
('Greeks', 0.545068621635437),
('Ioannis_Christou', 0.5400862693786621),
('Hrysopiyi_Devetzi', 0.5248444676399231),
('Heraklio', 0.5207759737968445),
('Athens_Greece', 0.516880989074707),
('Lithuania', 0.5166866183280945),
('Iraklion', 0.5146791934967041)]
Téléchargez les données d'évaluation du mot analogie, calculez vec (mot dans la deuxième colonne) --vec (mot dans la première colonne) + vec (mot dans la troisième colonne), et trouvez le mot avec la plus grande similitude avec le vecteur. , Trouvez la similitude. Ajoutez le mot obtenu et la similitude à la fin de chaque cas.
Télécharge les données spécifiées.
!wget http://download.tensorflow.org/data/questions-words.txt
#Vérifiez les 10 premières lignes
!head -10 questions-words.txt
production
: capital-common-countries
Athens Greece Baghdad Iraq
Athens Greece Bangkok Thailand
Athens Greece Beijing China
Athens Greece Berlin Germany
Athens Greece Bern Switzerland
Athens Greece Cairo Egypt
Athens Greece Canberra Australia
Athens Greece Hanoi Vietnam
Athens Greece Havana Cuba
Ces données comprennent un groupe pour évaluer les analogies sémantiques, comme (Athènes-Grèce, Tokyo-Japon), et un groupe pour évaluer les analogies grammaticales, comme (promenades, écriture-écriture). Je vais. Il se compose des 14 catégories suivantes au total, les 5 ci-dessus correspondent à la première et les autres correspondent à la seconde.
No. | Catégorie |
---|---|
1 | capital-common-countries |
2 | capital-world |
3 | currency |
4 | city-in-state |
5 | family |
6 | gram1-adjective-to-adverb |
7 | gram2-opposite |
8 | gram3-comparative |
9 | gram4-superlative |
10 | gram5-present-participle |
11 | gram6-nationality-adjective |
12 | gram7-past-tense |
13 | gram8-plural |
14 | gram9-plural-verbs |
Il lit ligne par ligne, calcule la similitude avec le mot spécifié et génère les données formatées.
with open('./questions-words.txt', 'r') as f1, open('./questions-words-add.txt', 'w') as f2:
for line in f1: #Lire ligne par ligne à partir de f1, ajouter le mot souhaité et la similitude, et écrire dans f2
line = line.split()
if line[0] == ':':
category = line[1]
else:
word, cos = model.most_similar(positive=[line[1], line[2]], negative=[line[0]], topn=1)[0]
f2.write(' '.join([category] + line + [word, str(cos) + '\n']))
!head -10 questions-words-add.txt
production
capital-common-countries Athens Greece Baghdad Iraq Iraqi 0.6351870894432068
capital-common-countries Athens Greece Bangkok Thailand Thailand 0.7137669324874878
capital-common-countries Athens Greece Beijing China China 0.7235777974128723
capital-common-countries Athens Greece Berlin Germany Germany 0.6734622120857239
capital-common-countries Athens Greece Bern Switzerland Switzerland 0.4919748306274414
capital-common-countries Athens Greece Cairo Egypt Egypt 0.7527809739112854
capital-common-countries Athens Greece Canberra Australia Australia 0.583732545375824
capital-common-countries Athens Greece Hanoi Vietnam Viet_Nam 0.6276341676712036
capital-common-countries Athens Greece Havana Cuba Cuba 0.6460992097854614
capital-common-countries Athens Greece Helsinki Finland Finland 0.6899983882904053
Mesurez le taux de précision de l'analogie sémantique et de l'analogie syntaxique en utilisant les résultats d'exécution> 64.
Calculez pour chaque catégorie correspondante.
with open('./questions-words-add.txt', 'r') as f:
sem_cnt = 0
sem_cor = 0
syn_cnt = 0
syn_cor = 0
for line in f:
line = line.split()
if not line[0].startswith('gram'):
sem_cnt += 1
if line[4] == line[5]:
sem_cor += 1
else:
syn_cnt += 1
if line[4] == line[5]:
syn_cor += 1
print(f'Taux de réponse correcte par analogie sémantique: {sem_cor/sem_cnt:.3f}')
print(f'Taux de réponse correcte par analogie littéraire: {syn_cor/syn_cnt:.3f}')
production
Taux de réponse correcte par analogie sémantique: 0.731
Taux de réponse correcte par analogie littéraire: 0.740
Téléchargez les données d'évaluation de The WordSimilarity-353 Test Collection et calculez le coefficient de corrélation de Spearman entre le classement de similarité calculé par vecteurs de mots et le classement du jugement de similarité humaine.
Ces données ont une similitude évaluée par l'homme avec une paire de mots. Calculez la similitude des vecteurs de mots pour chaque paire et calculez le coefficient de corrélation de rang de Spearman pour les deux.
!wget http://www.gabrilovich.com/resources/data/wordsim353/wordsim353.zip
!unzip wordsim353.zip
production
Archive: wordsim353.zip
inflating: combined.csv
inflating: set1.csv
inflating: set2.csv
inflating: combined.tab
inflating: set1.tab
inflating: set2.tab
inflating: instructions.txt
!head -10 './combined.csv'
production
Word 1,Word 2,Human (mean)
love,sex,6.77
tiger,cat,7.35
tiger,tiger,10.00
book,paper,7.46
computer,keyboard,7.62
computer,internet,7.58
plane,car,5.77
train,car,6.31
telephone,communication,7.50
ws353 = []
with open('./combined.csv', 'r') as f:
next(f)
for line in f: #Lire ligne par ligne et calculer le vecteur de mot et la similitude
line = [s.strip() for s in line.split(',')]
line.append(model.similarity(line[0], line[1]))
ws353.append(line)
#Vérification
for i in range(5):
print(ws353[i])
production
['love', 'sex', '6.77', 0.2639377]
['tiger', 'cat', '7.35', 0.5172962]
['tiger', 'tiger', '10.00', 0.99999994]
['book', 'paper', '7.46', 0.3634626]
['computer', 'keyboard', '7.62', 0.39639163]
import numpy as np
from scipy.stats import spearmanr
#Calcul du coefficient de corrélation de Spearman
human = np.array(ws353).T[2]
w2v = np.array(ws353).T[3]
correlation, pvalue = spearmanr(human, w2v)
print(f'Coefficient de corrélation de Spearman: {correlation:.3f}')
production
Coefficient de corrélation de Spearman: 0.685
Extraire le mot vecteur lié au nom du pays et exécuter le clustering k-means avec le nombre de clusters k = 5.
Comme nous n'avons pas pu trouver une source appropriée pour la liste des noms de pays, nous la collectons à partir des données d'évaluation du mot analogie.
#Acquisition du nom du pays
countries = set()
with open('./questions-words-add.txt') as f:
for line in f:
line = line.split()
if line[0] in ['capital-common-countries', 'capital-world']:
countries.add(line[2])
elif line[0] in ['currency', 'gram6-nationality-adjective']:
countries.add(line[1])
countries = list(countries)
#Obtenir le vecteur de mot
countries_vec = [model[country] for country in countries]
from sklearn.cluster import KMeans
# k-signifie regroupement
kmeans = KMeans(n_clusters=5)
kmeans.fit(countries_vec)
for i in range(5):
cluster = np.where(kmeans.labels_ == i)[0]
print('cluster', i)
print(', '.join([countries[k] for k in cluster]))
production
cluster 0
Taiwan, Afghanistan, Iraq, Lebanon, Indonesia, Turkey, Egypt, Libya, Syria, Korea, China, Nepal, Cambodia, India, Bhutan, Qatar, Laos, Malaysia, Iran, Vietnam, Oman, Bahrain, Pakistan, Thailand, Bangladesh, Morocco, Jordan, Israel
cluster 1
Madagascar, Uganda, Botswana, Guinea, Malawi, Tunisia, Nigeria, Mauritania, Kenya, Zambia, Algeria, Mozambique, Ghana, Niger, Somalia, Angola, Mali, Senegal, Sudan, Zimbabwe, Gambia, Eritrea, Liberia, Burundi, Gabon, Rwanda, Namibia
cluster 2
Suriname, Uruguay, Tuvalu, Nicaragua, Colombia, Belize, Venezuela, Ecuador, Fiji, Peru, Guyana, Jamaica, Brazil, Honduras, Samoa, Bahamas, Dominica, Philippines, Cuba, Chile, Mexico, Argentina
cluster 3
Netherlands, Sweden, USA, Ireland, Canada, Spain, Malta, Greenland, Europe, Greece, France, Austria, Norway, Finland, Australia, Japan, Iceland, England, Italy, Denmark, Belgium, Switzerland, Germany, Portugal, Liechtenstein
cluster 4
Croatia, Belarus, Uzbekistan, Latvia, Tajikistan, Slovakia, Ukraine, Hungary, Albania, Poland, Montenegro, Georgia, Russia, Kyrgyzstan, Armenia, Romania, Cyprus, Lithuania, Azerbaijan, Serbia, Slovenia, Turkmenistan, Moldova, Bulgaria, Estonia, Kazakhstan, Macedonia
Exécutez le regroupement hiérarchique par la méthode Ward pour les vecteurs de mots liés aux noms de pays. En outre, visualisez le résultat du regroupement sous forme de dendrogramme.
from matplotlib import pyplot as plt
from scipy.cluster.hierarchy import dendrogram, linkage
plt.figure(figsize=(15, 5))
Z = linkage(countries_vec, method='ward')
dendrogram(Z, labels=countries)
plt.show()
Visualisez l'espace vectoriel des vecteurs de mots liés aux noms de pays avec t-SNE.
Compressez le mot vecteur en deux dimensions avec t-SNE et visualisez-le dans un diagramme de dispersion.
!pip install bhtsne
import bhtsne
embedded = bhtsne.tsne(np.array(countries_vec).astype(np.float64), dimensions=2, rand_seed=123)
plt.figure(figsize=(10, 10))
plt.scatter(np.array(embedded).T[0], np.array(embedded).T[1])
for (x, y), name in zip(embedded, countries):
plt.annotate(name, (x, y))
plt.show()
Traitement du langage 100 coups sont conçus pour que vous puissiez apprendre non seulement le traitement du langage naturel lui-même, mais également le traitement des données de base et l'apprentissage automatique général. Même ceux qui étudient l'apprentissage automatique dans des cours en ligne pourront pratiquer de très bons résultats, alors essayez-le.
Recommended Posts