Transformers documentation

テキスト分類

You are viewing main version, which requires installation from source. If you'd like regular pip install, checkout the latest stable version (v5.22.1).
Hugging Face's logo
Join the Hugging Face community

and get access to the augmented documentation experience

to get started

テキスト分類

テキスト分類は、テキストにラベルまたはクラスを割り当てる一般的なNLPタスクです。大手企業の多くは、幅広い実用的なアプリケーションにおいて、テキスト分類を本番環境で運用しています。テキスト分類の最も人気のある形式の一つが感情分析で、これはテキストのシーケンスに🙂ポジティブ、🙁ネガティブ、😐ニュートラルなどのラベルを割り当てます。

このガイドでは、次の方法について説明します:

  1. IMDbデータセットでDistilBERTをファインチューニングし、映画レビューが肯定的か否定的かを判定します。
  2. ファインチューニングしたモデルを推論に使用します。

このタスクと互換性のあるすべてのアーキテクチャとチェックポイントを確認するには、タスクページを参照することをお勧めします。

開始前に、必要なライブラリがすべてインストールされていることを確認してください。

pip install transformers datasets evaluate accelerate

Hugging Face アカウントにログインして、モデルをアップロードし、コミュニティと共有できるようにすることを推奨します。プロンプトが表示されたら、ログイン用のトークンを入力してください:

>>> from huggingface_hub import notebook_login

>>> notebook_login()

IMDb データセットを読み込む

🤗 Datasets ライブラリから IMDb データセットを読み込むことから始めます:

>>> from datasets import load_dataset

>>> imdb = load_dataset("stanfordnlp/imdb")

次に、例を見てみましょう。

>>> imdb["test"][0]
{
    "label": 0,
    "text": "I love sci-fi and am willing to put up with a lot. Sci-fi movies/TV are usually underfunded, under-appreciated and misunderstood. I tried to like this, I really did, but it is to good TV sci-fi as Babylon 5 is to Star Trek (the original). Silly prosthetics, cheap cardboard sets, stilted dialogues, CG that doesn't match the background, and painfully one-dimensional characters cannot be overcome with a 'sci-fi' setting. (I'm sure there are those of you out there who think Babylon 5 is good sci-fi TV. It's not. It's clichéd and uninspiring.) While US viewers might like emotion and character development, sci-fi is a genre that does not take itself seriously (cf. Star Trek). It may treat important issues, yet not as a serious philosophy. It's really difficult to care about the characters here as they are not simply foolish, just missing a spark of life. Their actions and reactions are wooden and predictable, often painful to watch. The makers of Earth KNOW it's rubbish as they have to always say \"Gene Roddenberry's Earth...\" otherwise people would not continue watching. Roddenberry's ashes must be turning in their orbit as this dull, cheap, poorly edited (watching it without advert breaks really brings this home) trudging Trabant of a show lumbers into space. Spoiler. So, kill off a main character. And then bring him back as another actor. Jeeez! Dallas all over again.",
}

このデータセットには2つのフィールドがあります:

  • text: 映画のレビューテキスト。
  • label: ネガティブなレビューの場合は0、ポジティブなレビューの場合は1の値。

前処理

次のステップは、textフィールドの前処理のためにDistilBERTのトークナイザーを読み込むことです。

>>> from transformers import AutoTokenizer

>>> tokenizer = AutoTokenizer.from_pretrained("distilbert/distilbert-base-uncased")

text をトークナイズし、シーケンスを DistilBERT の最大入力長を超えないように切り詰める前処理関数を作成します:

>>> def preprocess_function(examples):
...     return tokenizer(examples["text"], truncation=True)

データセット全体に前処理関数を適用するには、🤗 Datasets の map 関数を使用します。batched=True を設定することで、データセットの複数の要素を一度に処理し、map を高速化できます:

tokenized_imdb = imdb.map(preprocess_function, batched=True)

次に、DataCollatorWithPadding を使用してバッチの例を作成します。データセット全体を最大長にパディングするのではなく、コラレーション時にバッチ内の最長長に合わせて動的にパディングする方が効率的です。

>>> from transformers import DataCollatorWithPadding

>>> data_collator = DataCollatorWithPadding(tokenizer=tokenizer)

評価

トレーニング中にメトリクスを含めることは、モデルの性能を評価する上で多くの場合、役立ちます。🤗 Evaluate ライブラリを使用すると、評価メソッドをすばやく読み込むことができます。このタスクでは、accuracy メトリクスを読み込みます(メトリクスの読み込みと計算方法の詳細については、🤗 Evaluate の クイックツアー を参照してください):

>>> import evaluate

>>> accuracy = evaluate.load("accuracy")

次に、予測値とラベルをcomputeに渡して正解率を計算する関数を作成します。

>>> import numpy as np


>>> def compute_metrics(eval_pred):
...     predictions, labels = eval_pred
...     predictions = np.argmax(predictions, axis=1)
...     return accuracy.compute(predictions=predictions, references=labels)

compute_metrics 関数はこれで準備が整いました。学習を設定する際に、この関数に戻ります。

学習

モデルの学習を開始する前に、id2labelとlabel2idを使用して、期待されるIDとラベルの対応表を作成します。

>>> id2label = {0: "NEGATIVE", 1: "POSITIVE"}
>>> label2id = {"NEGATIVE": 0, "POSITIVE": 1}

Trainer を用いたモデルのファインチューニングに慣れていない場合は、こちらの基本的なチュートリアルをご覧ください!

いよいよモデルの学習を開始できます!AutoModelForSequenceClassification を使用して DistilBERT を読み込み、期待されるラベル数とラベルのマッピングを指定します:

>>> from transformers import AutoModelForSequenceClassification, TrainingArguments, Trainer

>>> model = AutoModelForSequenceClassification.from_pretrained(
...     "distilbert/distilbert-base-uncased", num_labels=2, id2label=id2label, label2id=label2id
... )

この時点で、残りのステップは3つだけです:

  1. TrainingArguments で学習ハイパーパラメータを定義します。必須のパラメータは output_dir のみで、モデルの保存先を指定します。push_to_hub=True を設定することで、このモデルを Hub にプッシュできます(モデルをアップロードするには Hugging Face にサインインしている必要があります)。各エポックの終了時、Trainer は精度を評価し、学習チェックポイントを保存します。
  2. モデル、データセット、トークナイザー、データコラテーター、compute_metrics 関数とともに、学習引数を Trainer に渡します。
  3. train()を呼び出して、モデルをファインチューニングします。
>>> training_args = TrainingArguments(
...     output_dir="my_awesome_model",
...     learning_rate=2e-5,
...     per_device_train_batch_size=16,
...     per_device_eval_batch_size=16,
...     num_train_epochs=2,
...     weight_decay=0.01,
...     eval_strategy="epoch",
...     save_strategy="epoch",
...     load_best_model_at_end=True,
...     push_to_hub=True,
... )

>>> trainer = Trainer(
...     model=model,
...     args=training_args,
...     train_dataset=tokenized_imdb["train"],
...     eval_dataset=tokenized_imdb["test"],
...     processing_class=tokenizer,
...     data_collator=data_collator,
...     compute_metrics=compute_metrics,
... )

>>> trainer.train()

tokenizer を Trainer に渡すと、デフォルトで動的パディングが適用されます。この場合、データコラテーターを明示的に指定する必要はありません。

トレーニングが完了したら、push_to_hub() メソッドでモデルを Hub に共有し、誰でもそのモデルを利用できるようにしてください。

>>> trainer.push_to_hub()

テキスト分類用のモデルをファインチューニングする方法について、より詳細な例を確認するには、対応するPyTorchノートブックをご覧ください。

推論

素晴らしいですね。モデルのファインチューニングが完了したので、推論に使用できます!

推論を実行したいテキストを用意してください:

>>> text = "This was a masterpiece. Not completely faithful to the books, but enthralling from beginning to end. Might be my favorite of the three."

ファインチューニングしたモデルを推論で試す最も簡単な方法は、pipeline()でそれを使用することです。モデルを指定して感情分析用のpipelineをインスタンス化し、テキストを渡します:

>>> from transformers import pipeline

>>> classifier = pipeline("sentiment-analysis", model="stevhliu/my_awesome_model")
>>> classifier(text)
[{'label': 'POSITIVE', 'score': 0.9994940757751465}]

必要に応じて、pipelineの結果を手動で再現することもできます。

テキストをトークン化し、PyTorch テンソルを返します:

>>> from transformers import AutoTokenizer

>>> tokenizer = AutoTokenizer.from_pretrained("stevhliu/my_awesome_model")
>>> inputs = tokenizer(text, return_tensors="pt")

入力をモデルに渡し、logitsを返します:

>>> import torch
>>> from transformers import AutoModelForSequenceClassification

>>> model = AutoModelForSequenceClassification.from_pretrained("stevhliu/my_awesome_model")
>>> with torch.no_grad():
...     logits = model(**inputs).logits

確率が最も高いクラスを取得し、モデルのid2labelマッピングを使用してテキストラベルに変換します:

>>> predicted_class_id = logits.argmax().item()
>>> model.config.id2label[predicted_class_id]
'POSITIVE'
Update on GitHub