LoginSignup
14
15

More than 3 years have passed since last update.

Hugging Faceのライブラリを使ってTokenize

Last updated at Posted at 2020-05-10

背景

最近、kaggleを始めました。
Tweetから文字列を抽出するコンテストなんですが、数打ちゃ当たるでは?と思い、色んな手法で単語を特徴量変換してみました。
その時に、便利だったToknizerをご紹介します。
※Pythonのライブラリです。

Tokenizerとは?

機械学習で言葉を学習させるためには、その言葉を数値化(ベクトル化)する必要があります。その変換器のことを、Tokenizerと言います。おそらく。
例えば、
 This -> Tokenizer ->713
のように、数値化します。

transformers

今回使うライブラリは「Hugging Face, Inc」が開発している「transformers」というライブラリを使います。
自然言語処理だとお馴染みのライブラリ(少なくともkaggleではよく使われてた)で、tokenizerだけでなく、最新の手法によるmodelも実装されています。

さっそく使ってみましょう

今回は「RoBERTa」を例として使ってみます。
ソースはここにあります。
このソースはipynb形式なので、Google Colabか、Visual Studio Codeで実行できます。
Google Colab
Visual Studio Code
または、コードをそれぞれ取り出して、コンソールやpyに移植して試してみてください。

tokenizerを取得

transformers.AutoTokenizer.from_pretrained(モデル名)でtokenizerを取得します。「モデル名」を変えることで、そのモデルのtokenizerを取得でます。今回はRoBERTaを使うので、「roberta-base」を入力。他のモデルはここにあります。
生成されるまで時間がかかるので、少々お待ちを。

import transformers

tokenizer = transformers.AutoTokenizer.from_pretrained("roberta-base")

適当な文を作成

今回は下記の文を用意。

text = "This is a pen."
text2 = "I am a man"

ベクトル化

作成した文をそれぞれベクトル化します。それには、encode(テキスト)を使います。

ids = tokenizer.encode(text)
# output
# [713, 16, 10, 7670, 4]
ids2 = tokenizer.encode(text2)
# output
# [100, 524, 10, 313]

これでやりたかった言葉の数値ができましたね。
一文目をみてみると、
this -> 713
is -> 16
a -> 10
pen -> 7670
. -> 4
に変換されました!!!

Special Token

Special Tokenとは?

さらに、BERTやRoBERTaといた手法では、特別な文字を使って学習をしています。文の先頭や文と文の切れ目を表す文字などです。
詳しくはここをチェックして見てください。
例えば、RoBERTaではどういう文字が使われているかみてましょう。
special_tokens_mapという変数に詰められています。

tokenizer.special_tokens_map
# output
# {'bos_token': '<s>',
#  'eos_token': '</s>',
#  'unk_token': '<unk>',
#  'sep_token': '</s>',
#  'pad_token': '<pad>',
#  'cls_token': '<s>',
#  'mask_token': '<mask>'}

「トークンの意味: トークンに割り当てられて文字」
というような出力となっています。
例えば、一つ目のbos_tokenには<s>という文字が割り当てられています。
また、それぞれの意味としては、
bos_token: 文の先頭(Begin of sequence token)
eos_token: 文のおしり(End of Sequence token)
unk_token: IDに変換できない文字(Unknown token)
sep_token: 文と文を区切り目(The separator token)
pad_token: パッディング(The token used for padding)
cls_token: 分類用(cls_token)
mask_token: マスク(The token used for masking values)

です。詳しい説明は先ほど挙げたURLで確認してみてください。

Special TokenのIDチェック

all_special_tokensはSpecial Tokenに割り当てられた文字リスト、all_special_idsには先程のSpecial Tokenに対応するIDが詰められています。all_special_tokensと同じ順で並んでいます。
先程7つのSpecial Tokenがあげられましたが、割り当てられた文字が重複しているものもあるので、all_special_tokensは5つの文字リストになっています。

tokenizer.all_special_tokens
# output
# ['<pad>', '<s>', '<mask>', '<unk>', '</s>']
tokenizer.all_special_ids
# output
# [1, 0, 50264, 3, 2]

Special Tokenを追加

RoBERTaやBERTではModelで学習、推論する時にSpecial Tokenを追加する必要があります。(今回はパディングはしていません。)
先ほど調べたSpecial Tokenを手動でくっつけてもよいですが、自動で入力した文にSpecial Tokenを追加してくれるAPIが用意されているので、それを使ってみます。

ids_with_special_token = tokenizer.build_inputs_with_special_tokens(ids, ids2)
# output(ids_with_special_token)
# [0, 713, 16, 10, 7670, 4, 2, 2, 100, 524, 10, 313, 2]
mask = tokenizer.get_special_tokens_mask(ids, ids2)
# output(mask)
# [1, 0, 0, 0, 0, 0, 1, 1, 0, 0, 0, 0, 1]

Special Tokenの追加には、
tokenizer.build_inputs_with_special_tokens(テキストID、テキスト2ID)
を使います。2つ文を入れるいれることができ(1つでもOK)、ちゃんと2文の頭、区切り目、おしりにSpecial Tokenが挿入されていますね。

今後は、実際にModelで処理させてみます。

14
15
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
14
15