[PYTHON] J'ai essayé 100 traitements linguistiques Knock 2020: Chapitre 4

introduction

J'ai essayé Language processing 100 knock 2020. Vous pouvez voir le lien des autres chapitres d'ici, et le code source de ici.

Chapitre 4 Analyse morphologique

N ° 30 Lecture des résultats d'analyses morphologiques

Implémentez un programme qui lit les résultats de l'analyse morphologique (neko.txt.mecab). Cependant, chaque élément morphologique est stocké dans un type de mappage avec la clé de la forme de surface (surface), de la forme de base (base), d'une partie du mot (pos) et d'une partie du mot sous-classification 1 (pos1), et une phrase est exprimée sous forme d'une liste d'éléments morphologiques (type de mappage). Faisons le. Pour le reste des problèmes du chapitre 4, utilisez le programme créé ici.

<détails>

Réponse </ summary>

030.py


import pandas as pd

with open(file="neko.txt.mecab", mode="rt", encoding="utf-8") as neko:
    nekotext = neko.readlines()

nekolist = []
for str in nekotext:
    list = str.replace("\n", "").replace(" ", "").replace("\t", ",").split(",")
    if list[0] != "EOS": nekolist.append([list[0], list[7], list[1], list[2]])
    else: nekolist.append([list[0], "*", "*", "*"])
pd.set_option('display.unicode.east_asian_width', True)
df_neko = pd.DataFrame(nekolist, columns=["surface", "base", "pos", "pos1"])
print(df_neko)


# ->          surface      base     pos                      pos1
#0 11 substantif nombre
#1 Symbole vide
#2 Je suis je suis synonyme
#3 est un assistant
#4 chat chat nomenclature générale...
Commentaires

Je l'ai mis ensemble dans pandas, mais ... c'est pratique, ça ressemble à un type de mapping, n'est-ce pas? (Non)

N ° 31 verbe

Extraire toutes les formes de surface du verbe.

<détails>

Réponse </ summary>

031.py


import input_neko as nk

df = nk.input()
print(df.query("pos == 'verbe'")["surface"].values.tolist())

# -> ['Née', 'Tsuka', 'Shi', 'Pleurs',...
Commentaires

J'utilise le résultat du n ° 30 comme «import». Le type «Série» et le type «liste» peuvent être convertis l'un à l'autre, ce qui est pratique.

No.32 Prototype du verbe

Extraire toutes les formes originales du verbe.

<détails>

Réponse </ summary>

032.py


import input_neko as nk

df = nk.input()
print(df.query("pos == 'verbe'")["base"].values.tolist())

# -> ['Être né', 'Tsukuri', 'Faire', 'cri',...
Commentaires

La «surface» du n ° 31 vient de changer en «base».

N ° 33 "A B"

Extraire la nomenclature dans laquelle deux nomenclatures sont reliées par "non".

<détails>

Réponse </ summary>

033.py


import input_neko as nk

df = nk.input()
df.reset_index()
list_index = df.query("surface == 'de' & pos == 'Particule'").index
print([f"{df.iloc[item-1,1]}de{df.iloc[item+1,1]}" for item in list_index if df.iloc[item-1, 2] == df.iloc[item+1, 2] == "nom"])

# -> ['Sa paume', 'Sur la paume', 'Visage de l'élève', 'Devrait faire face',...
Commentaires

Je pensais que je pourrais le sortir avec df.iloc [item-1: item + 1, 1], mais ça n'a pas fonctionné, donc j'ai fini avec un long code.

N ° 34 Connexion nomenclature

Extraire la concaténation de la nomenclature (noms qui apparaissent consécutivement) avec la correspondance la plus longue.

<détails>

Réponse </ summary>

034.py


import input_neko as nk

df = nk.input()
df.reset_index()
num = 0
str = ""
ans = []
for i in range(len(df)):
    if df.iloc[i, 2] == "nom":
        num = num + 1
        str = str + df.iloc[i, 0]
    else:
        if num >= 2:
            ans.append(str)
        num = 0
        str = ""
print(ans)

# -> ['Chez l'homme', 'Le pire', 'Opportun', 'Un cheveu',...
Commentaires

Ajoutez la nomenclature à «str» et ajoutez-la à «an» lorsqu'il y a deux contiguïtés de nomenclature ou plus.

Fréquence d'apparition des mots n ° 35

Trouvez les mots qui apparaissent dans la phrase et leur fréquence d'apparition, et classez-les par ordre décroissant de fréquence d'apparition.

<détails>

Réponse </ summary>

035.py


import input_neko as nk

df = nk.input()
print(df["surface"].value_counts().to_dict())

# -> {'de': 9194, '。': 7486, 'main': 6868, '、': 6772,...
Commentaires

On dit que "Series" est pratique car il peut également être converti en type "dict".

N ° 36 Top 10 des mots les plus fréquents

Affichez les 10 mots avec une fréquence d'apparition élevée et leur fréquence d'apparition dans un graphique (par exemple, un histogramme).

<détails>

Réponse </ summary>

036.py


import input_neko as nk
import japanize_matplotlib
import matplotlib.pyplot as plt


df = nk.input()
df_dict = df["surface"].value_counts()[:10].to_dict()
left = list(df_dict.keys())
height = list(df_dict.values())
fig = plt.figure()
plt.bar(left, height)
plt.show()
fig.savefig("036_graph.png ")

# ->

036_graph.png

Commentaires

Il a fallu beaucoup de temps pour activer les caractères japonais de matplotlib, mais je l'ai résolu en insérant japanize_matplotlib.

No.37 Top 10 des mots qui cohabitent fréquemment avec "chat"

Afficher 10 mots qui co-apparaissent souvent avec "chat" (haute fréquence de cooccurrence) et leur fréquence d'apparition dans un graphique (par exemple, un graphique à barres).

<détails>

Réponse </ summary>

037.py


from collections import defaultdict
import input_neko as nk
import japanize_matplotlib
import matplotlib.pyplot as plt

df = nk.input()
start = 0
neko_phrase = []
freq = defaultdict(int)
for i in range(len(df)):
    if df.iloc[i, 0] == "EOS":
        phrase = df.iloc[start:i, 0].to_list()
        if "Chat" in phrase:
            neko_phrase.append(phrase)
            for word in phrase:
                if word != "Chat":  freq[word] += 1
        start = i + 1
neko_relation = sorted(freq.items(), key=lambda x: x[1], reverse=True)[:10]
left = [item[0] for item in neko_relation]
height = [item[1] for item in neko_relation]
fig = plt.figure()
plt.bar(left, height)
fig.savefig("037_graph.png ")

# -> 

037_graph.png

Commentaires

Les mots qui apparaissent souvent dans des phrases incluant des chats sont comptés comme ayant une fréquence élevée de cooccurrence. Une expression lambda est utilisée au milieu pour trier par la valeur value de type dict.

Histogramme n ° 38

Tracez un histogramme de la fréquence d'occurrence des mots (l'axe horizontal représente la fréquence d'occurrence et l'axe vertical représente le nombre de types de mots qui prennent la fréquence d'occurrence sous forme de graphique à barres).

<détails>

Réponse </ summary>

038.py


import input_neko as nk
import pandas as pd
import japanize_matplotlib
import matplotlib.pyplot as plt

df = nk.input()
df_dict = df["surface"].value_counts().to_dict()
word = list(df_dict.keys())
count = list(df_dict.values())
d = pd.DataFrame(count, index=word).groupby(0).size()
height = list(d[:10])
fig = plt.figure()
plt.bar(range(1, 11), height)
fig.savefig("038_graph.png ")

# -> 

038_graph.png

Commentaires

J'ai pensé que je devrais utiliser groupby, mais je pense que la conversion de dict, DataFrame, Series, list a rendu la compréhension plus difficile ...

N ° 39 Loi Zipf

Tracez les deux graphiques logarithmiques avec le classement de la fréquence des mots sur l'axe horizontal et la fréquence des mots sur l'axe vertical.

<détails>

Réponse </ summary>

039.py


import input_neko as nk
import pandas as pd
import japanize_matplotlib
import matplotlib.pyplot as plt

df = nk.input()
df_dict = df["surface"].value_counts().to_dict()
word = list(df_dict.keys())
count = list(df_dict.values())
d = pd.DataFrame(count, index=word).groupby(0).size()
height = list(d[:])
fig = plt.figure()
plt.xscale("log")
plt.yscale("log")
plt.plot(range(len(height)), height)
fig.savefig("039_graph.png ")

# -> 

039_graph.png

Commentaires

[Wikipédia](https://ja.wikipedia.org/wiki/%E3%82%B8%E3%83%83%E3%83%97%E3%81%AE%E6%B3%95%E5%89 J'ai vérifié la loi de Zipf avec% 87).

La loi de Zip (loi de Zipf) ou loi de Zipf est une règle empirique selon laquelle le k-ème élément le plus fréquent représente 1 / k du total.

Idéalement, si vous prenez un graphique logarithmique sur les deux axes, ce sera une ligne droite qui descend vers la droite, mais je pense que les résultats de sortie sont généralement les mêmes. Il semble étrange que la loi de Zipf apparaisse dans diverses situations.

Recommended Posts