自然言語処理

これから自然言語処理を始めるならspaCyがおすすめ!0からのspaCy入門

今回はPythonを使った自然言語処理の世界に足を踏み入れたい初心者の皆さんに、とても便利なツール「spaCy」(“スペイシー”と読みます)について紹介します。

自然言語処理は、データ分析のさまざまな分野の中でも一般にかなり難しい分野と思われていることが多いのですが、spaCyを用いるとさまざまな自然言語処理の技術を短いコードで簡単に扱えるようになるため、入門者はスムーズにその一歩目を進めることができます。

難しい分野だからとこれまで自然言語処理をと遠ざけてきた人、これから自然言語処理を始めてみたいと思っている人は、是非この記事を読んでみてください。

この記事でわかること

  • spaCyの使い方がわかる
  • 自然言語処理の基本的な手法がわかる
  • 自然言語処理を使ってできることのイメージが持てるようになる

本ブログを運営しているTech Teacherは、
プログラミング家庭教師サービスを運営しています。
完全マンツーマン・フルオーダーメイド
あなたが必要な指導を提供します。

spaCyとは

spaCyは、PythonとCython(というプログラミング言語)で作られた、実務で使える高速な自然言語処理のツールです。自然言語処理とは、コンピュータによって人の言葉を解析して様々な処理する技術のことを指します。つまり、このライブラリはたくさんの文章を効率よく処理するためのツールです。

Pythonで使える自然言語処理のツールは、他にもNLTKやTextBlobなど、いくつかあります。しかし、spaCyは特に実務での使用を目的に、大量の文章を高速に処理することができるライブラリになっています。例えばウェブサイトから情報を集めるときや、SNSの投稿を分析するときなどに、大変役立ちます。

spaCyの代表的な機能

spaCyにはたくさんの機能がありますが、以下は特に基本的なもの(よく使われるもの)です。

  • さまざまな統計モデル
  • トークン化
  • 品詞と依存関係の解析
  • 単語ベクトル化

さまざまな統計モデル

spaCyは(日本語を含む)さまざまな言語の学習済みのモデルを持っていて、これを使うことで文章の解析ができます。「モデル」という言葉に馴染みがない人は、さまざまな言語に応じた解析用の「道具」を持っている、と考えてください。

トークン化

トークン化とは文章を単語や記号に分けることを言います。自然言語処理では欠かせない機能です。たとえば「我輩は猫である。」という文章をトークン化すると「我輩/は/猫/で/ある/。」となります。また、「我輩」「は」「猫」など1つ1つの単語をトークンと呼びます。

品詞と依存関係の解析

文章に含まれる各単語の品詞(名詞、動詞など)を与えることや、文章中における単語と単語の依存関係(修飾関係)を与えることができます。たとえば「太郎は花子が持っている本を読んだ。」という文章の品詞と依存関係を解析すると、「読んだ」が主文の動詞、「太郎」は「読んだ」の主語(nsubj)、「本」は「読んだ」の目的語(dobj)、「持っている」は「本」を修飾する関係(acl)にあり、「花子」は「持っている」の主語(nsubj)、という解析が行われます。

Pythonで形態素解析するには?コードから結果の出力まで解説!形態素解析の実際のやり方にお困りの方は必見!この記事ではPythonでの形態素解析方法を説明します。形態素解析の基礎的な知識 はもちろんのこと、実際にMeCabとjanomeを使ったプログラミングコードとその形態素解析の例をお見せします。この記事を見れば、簡単な形態素解析が今すぐできるようになります。...

単語ベクトル化

各単語を数ベクトル(数の集まり)で表すことができます。具体的には、例えば「猫」というトークンを[ 12, 42, 22, 12, 11 ]という数の集まりとして表現することを言います(ここで数は適当です。意味はありません。)これを使うと単語同士が似ているかどうか(単語の類似度)を見ることができます。

他にも自然言語処理に不可欠な、もしくは有用な様々な機能が提供されています。

【1分で理解】文章を数値化する技術Bag of Wordsとは?本記事ではまず、機械学習の1分野である自然言語処理について紹介します。そして、BoWやその他の文字列を数値化する技術(TF-IDF,Word2Vec)を取り上げ、BoWの応用方法ついて解説します。...

spaCyを使ってみよう!使用例

spaCyのいくつかの機能を実際に使用して体験してみましょう。ここではGoogle Colaboratoryを使用しています。
まずはセルに以下のコマンドを入力してspaCyをインストールしておきます。

!pip install spacy

統計モデルの利用とトークン化

まずは英語解析用のモデルを読み込み、モデルを使って英語の文章(”Apple is looking at buying U.K. startup for $1 billion”)をトークン化してみます。トークン化はロードしたモデルに対象の文章をインプットすることで行うことができます。

import spacy # spaCyをimport

nlp = spacy.load("en_core_web_sm") # 英語用のモデルを読み込む

#モデルに解析したい文章をインプット
#解析されたdocオブジェクトが返される
doc = nlp("Apple is looking at buying U.K. startup for $1 billion")

#docオブジェクトからは以下のようにして各トークンの属性を参照できる
#text属性:各トークンのテキスト
#pos_性:各トークンの品詞
for token in doc:
print(token.text, token.pos_)

OUTPUT:

Apple PROPN
is AUX
looking VERB
at ADP
buying VERB
U.K. PROPN
startup NOUN
for ADP
$ SYM
1 NUM
billion NUM

OUTPUTを見てみましょう。

“Apple is looking at buying U.K. startup for $1 billion”という文章を解析して、各トークンとトークンの品詞を表示しています。

例えば出力の1行目からは、この文章にAppleという単語が含まれていて、その品詞が名詞(PROPN)である、ということがわかります。

単語ベクトル化と類似度

トークンを単語ベクトル化(単語を配列で表現すること)した形を参照するにはvector属性を参照します。

nlp = spacy.load("en_core_web_md")
tokens = nlp("This is a sentence.")

for token in tokens:
    print(token.vector)

OUTPUT:

[ 1.6849 1.9826 -0.77743 -4.7383 5.5418 -1.6226
6.2955 0.22745 0.31281 -3.1494 6.3609 -1.3135
-2.6258 0.63158 1.1777 -3.375 5.1428 5.9062
2.5124 2.3085 -3.2811 4.9603 0.92932 0.074527
-1.4698 -1.9482 -8.2695 1.8833 -5.7618 3.5629
0.66097 -2.5866 -0.25952 1.503 -4.8224 -4.5838
-0.018427 1.2355 6.5986 -0.1242 -5.2059 2.1204
-0.26518 -1.5424 -4.6138 0.75889 1.7107 1.9419
-6.6123 0.44145 0.91669 -2.0622 -1.019 -1.6192
・・・]

OUTPUTは一部のみ掲載しています。

例えば最初の配列[ 1.6849 1.9826 -0.77743 ・・・ -1.8289 -2.9454 -0.83337 ]は”This”というトークンを単語ベクトル化したものです。

トークンを単語ベクトル(数値ベクトル)に表現することにはさまざまなメリットがあります。例えばベクトルの各値が近いトークン同士は意味が近いトークンを表します。トークンの意味の類似性をベクトルの値の近さによって数値的に計算できるのです。

もっともトークンの類似度は、単語ベクトル化したトークンを用いて計算をしなくても、similarityメソッドを用いて直接求めることができます。

# "king"と"queen"という単語がどれくらい似ているかを見る
token1 = nlp("king")
token2 = nlp("queen")
similarity = token1.similarity(token2)
print(similarity)

OUTPUT:

0.5099376221161971

類似度は0~1の間の値で与えられ1に近いほど類似度が高いです。例えば、全く同じ単語(今回は”king”と”king”)で類似度を求めると、最大値1が返されます。

token1 = nlp("king")
token2 = nlp("king")
similarity = token1.similarity(token2)
print(similarity)

OUTPUT:

1.0

日本語文書の処理

spaCyは日本語の文章も読み取ることができます。日本語のモデルを使うためには、例えばja_core_news_smというモデルを使います。このモデルを導入することで、日本語の文章も解析できるようになります。

!python -m spacy download ja_core_news_sm
nlp = spacy.load("ja_core_news_sm")
doc = nlp("我輩は猫である。")
print(doc.text)
for token in doc:
    print(token.text, token.pos_)

OUTPUT:

我輩は猫である。
我輩 PROPN
は ADP
猫 NOUN
で AUX
ある VERB
。 PUNCT

日本語についてもトークン化と品詞の判別を行うことができました。

そのほか、日本語を対象として、自然言語処理におけるいくつかの基本処理を紹介しておきましょう。

トークンの各位置(文章中のインデックス)をidx属性で参照する

text = "親譲りの無鉄砲で子供の時から損ばかりしている。小学校に居る時分学校の二階から飛び降りて一週間程腰を抜かした事がある。なぜそんな無闇をしたと聞く人があるかもしれぬ。別段深い理由でもない。新築の二階から首を出していたら,同級生の一人が冗談に,いくら威張っても,そこから飛び降りる事は出来まい。弱虫や-い。と囃し立てたからである。小使いに負ぶさって帰ってきた時,おやじが大きな眼をして二階位から飛び降りて腰を抜かす奴があるかと云ったから,この次は抜かさずに飛んで見せますと答えた。"
nlp = spacy.load("ja_core_news_sm")
doc = nlp(text)
print(doc.text)
for token in doc:
    print(token.text, token.idx)

OUTPUT:

親 0
譲り 1
の 3
無鉄砲 4
で 7
子供 8
の 10
時 11
から 12
損 14
・・・(略)・・・

例えば「無鉄砲」という言葉が登場するのはインデックス4(文章の5文字目)からであることがわかります。

単語の頻度を出力する

各文章の特徴は、その文章にどのような単語がどのくらいの頻度現れるかを確認することで理解することができます。そのため、自然言語処理では文章中の単語の頻度を求めることは、基本的な処理としてよく行われます。

頻度を求めるにはcollectionsモジュールのCounterクラスを使います。docには前のセルで取得したdocオブジェクトが代入されています(前節セルに続けて実行してください。)

from collections import Counter

words = [ token.text for token in doc]  #トークンのリストを作成

print(Counter(words)) #トークンごとに頻度を表示

OUTPUT:

Counter({‘て’: 8, ‘。’: 8, ‘から’: 7, ‘た’: 6, ‘の’: 5, ‘を’: 5, ‘が’: 5, ‘,’: 5, ‘で’: 4,・・・, ‘答え’: 1})

例えば、「答え」という単語は1回のみ登場していることが確認できます。

ストップワードを除去する

ストップワードとは、文章の中で頻繁に出現するが、その文章の内容や意味を理解する上であまり重要ではない単語のことを指します。例えば、日本語で「の」「は」「と」、英語で “the”、”is”、”and” などがストップワードに該当します。

上の例ではストップワードも含めた単語の頻度を求めていますが、ここではストップワードを除外した単語の頻度を求めてみます。ストップワードかどうかはis_stop属性を参照することで確認ができます。

from collections import Counter

words = [ token.text for token in doc if not token.is_stop ]  #ストップワードを除外したトークンのリストを作成

print(Counter(words))

OUTPUT:

Counter({‘。’: 8, ‘,’: 5, ‘二’: 3, ‘飛び’: 3, ‘時’: 2, ‘学校’: 2, ‘階’: 2, ‘降り’: 2,・・・, ‘飛ん’: 1, ‘見せ’: 1, ‘答え’: 1})

「てにをは」のような単語(トークン)が除外されていることが確認できます。

データサイエンスを学ぶなら家庭教師Tech Teacher!

『Tech Teacher』3つの魅力

魅力1. オーダーメイドのカリキュラ

『Tech Teacher』では、決められたカリキュラムがなくオーダーメイドでカリキュラムを組んでいます。「質問だけしたい」「相談相手が欲しい」等のご要望も実現できます。

    魅力2. 担当教師によるマンツーマン指導

    Tech Teacherでは完全マンツーマン指導で目標達成までサポートします。
    東京大学を始めとする難関大学の理系学生・院生・博士の教師がが1対1で、丁寧に指導しています。
    そのため、理解できない箇所は何度も分かるまで説明を受けることができます。

    魅力3. 3,960円/30分で必要な分だけ受講

    Tech Teacherでは、授業を受けた分だけ後払いの「従量課金制」を採用しているので、必要な分だけ授業を受講することができます。また、初期費用は入会金22,000円のみです一般的なプログラミングスクールとは異なり、多額な初期費用がかからないため、気軽に学習を始めることができます。

    まとめ

    ・魅力1. 担当教師によるマンツーマン指導

    ・魅力2. オーダーメイドのカリキュラム

    ・魅力3. 3,960円/30分で必要な分だけ受講

    質問のみのお問い合わせも受け付けております。

    まとめ

    spaCyはその速さと正確さから、たくさんの人たちに使われています。今回のブログで紹介したコードを見てもわかる通り、初めてプログラミングや自然言語処理を学ぶ人にとっても、spaCyは使いやすいツールと言えるでしょう。

    特に、日本語を含む色々な言語に対応しているので、様々な文章を読み取ることができます。spaCyから自然言語処理の世界を始めみるのはいかがでしょうか。

    なお今回のブログでは、トークン化のアルゴリズムや、単語ベクトル化のロジックなど、理論的な解説は行っておりません。これらの概念についても、自然言語処理を使いこなすにはいずれはきちんと理解する必要があります。

    理論を場合も、単に教科書で理論を学ぶよりも、実際にコーディングをして入力と出力の結果を見ながら学ぶ方が、より理解が深まります。そのような時にもspaCyは役立つでしょう。