日本語GPT-2モデルを用いて日本語文章を自動生成


# Overview
- 目的
    - 日本語GPT-2モデルを用いて、日本語文章を推論する。目的としては、DeepLearningによる記事作成がどの程度可能なのかを検証するために実施する。
- 結果
    - 最終的な校閲の仕事は残りつつも文章作ること自体は可能であることがわかった。
    - 学習の際に、記事に特化したデータを十分に抽出させることで、より精度の高い文章を生成することができるのではないかと思う。
    - 記事は記事でも各分野(政治、経済、ビジネス、文化、etc)に特化したmodelsを作成するなどすることにより多様な記事を書くことができそう。



# 実行環境
- Google Colaboratory
## ライブラリ
- torch==1.10.0+cu111
- transformers==4.4.2
- datasets==1.18.2
- sentencepiece==0.1.96

# 必要なライブラリをインストール

`pip`コマンドより、必要なライブラリをインストールする。
※以下のコマンドは`jupyter notebook`, `Google Colaboratory`上で実行することを想定して記述しています。

```bash
!pip install transformers==4.4.2
!pip install datasets==1.18.2
!pip install sentencepiece==0.1.96
```

# 日本語GPT-2モデルを用いて日本語文章を自動生成

## Pre-Trained Modelを利用

学習済みのモデルを利用して、推論を実施する。
学習済みモデルについては、以下のpublic datasetを利用して学習している。
[CC100-Japanese](https://metatext.io/datasets/cc100-japanese)
[Japanese Wikipedia](https://dumps.wikimedia.org/other/cirrussearch/)
チューニングの処理については後続の手順の中で実施する。

```python
from transformers import T5Tokenizer, AutoModelForCausalLM

# load tokenizer
tokenizer = T5Tokenizer.from_pretrained("rinna/japanese-gpt2-medium")

# load pre-trained model
model = AutoModelForCausalLM.from_pretrained("rinna/japanese-gpt2-medium")

# Set input word
input = tokenizer.encode("近年人工知能の活用は著しく上昇している。", return_tensors="pt")

# inference
output = model.generate(input, do_sample=True, max_length=30, num_return_sequences=3)

# inferred output
print(tokenizer.batch_decode(output))
```

### Output
```
['近年人工知能の活用は著しく上昇している。
 人工知能が活用される場面は、コンピューター上での様々な研究により様々な分野に拡大しており、人間が', '近年人工知能の活用は著しく上昇している。
 aiは膨大な数の情報を処理するため、機械学習だけで処理できない場合、その情報をもとにモデルを構築し', '近年人工知能の活用は著しく上昇している。
 人工知能(ai)、人工知能を活用したビジネス、事業を行う際の知見を共有する機会を創出する']
```

## Pre-Trained ModelをFine Tuning

### Fine Tuningリソースの取得

Fune Tuningnに利用する`huggingface/transformers`をcloneしてくる。
```bash
# GoogleDriveをマウント
from google.colab import drive 
drive.mount('/content/drive')

# MyDrive配下に移動
%cd '/content/drive/My Drive/Colab Notebooks/'

# MyDrive配下にClone
!git clone https://github.com/huggingface/transformers -b v4.4.2
```

cloneしたリソース内の`./transformers/examples/language-modeling/run_clm.py`を一部修正する。
`AutoTokenizer`では、読み込みができないため明示的に、`T5Tokenizer`を指定して読み込む。

```diff
from transformers import (
    CONFIG_MAPPING,
    MODEL_FOR_CAUSAL_LM_MAPPING,
    AutoConfig,
    AutoModelForCausalLM,
    AutoTokenizer,
    HfArgumentParser,
    Trainer,
    TrainingArguments,
    default_data_collator,
    set_seed,
-   AutoTokenizer,
+   T5Tokenizer,

- tokenizer = AutoTokenizer.from_pretrained(model_args.tokenizer_name, **tokenizer_kwargs)
+ tokenizer = T5Tokenizer.from_pretrained(model_args.tokenizer_name, **tokenizer_kwargs)

- tokenizer = AutoTokenizer.from_pretrained(model_args.model_name_or_path, **tokenizer_kwargs)
+ tokenizer = T5Tokenizer.from_pretrained(model_args.model_name_or_path, **tokenizer_kwargs)
```

### データセットの準備
修正が完了したら、Driveの`My Drive/Colab Notebooks`フォルダ配下に`dataset.txt`再学習データセットを配置する。
サンプルのデータセットについては、[こちら](https://github.com/npaka3/akane-talk/blob/main/docs/dataset.txt)を参照。

```bash
from google.colab import drive 
drive.mount('/content/drive')

# My Drive/Colab Notebooks フォルダに移動
%cd '/content/drive/My Drive/Colab Notebooks/'

# フォルダ内のリソース出力（dataset.txtが存在すること!!）
!ls -ltr
```

### Fine Tuning実行

では、My Drive/Colab Notebooks フォルダに`dataset.txt`を配置したら
以下のコマンドを実行し、Fine Tuningを実施する。
`Google Colaboratory`で実行する場合、メモリ不足となるためProにアップグレードする必要がある。

```bash
from google.colab import drive 
drive.mount('/content/drive')


# My Drive/Colab Notebooks フォルダに移動
%cd '/content/drive/My Drive/Colab Notebooks/'

# 処理時間計測
%time

# fine tuning実行
!python ./transformers/examples/language-modeling/run_clm.py \
    --model_name_or_path=rinna/japanese-gpt2-medium \
    --train_file=./akane-talk/docs/dataset.txt \
    --validation_file=./akane-talk/docs/dataset.txt \
    --do_train \
    --do_eval \
    --num_train_epochs=3 \
    --save_steps=5000 \
    --save_total_limit=3 \
    --per_device_train_batch_size=1 \
    --per_device_eval_batch_size=1 \
    --output_dir=output/ \
    --use_fast_tokenizer=False
```

## Fine Tuningしたモデルにて再度推論

チューニングしたモデルにて再度推論をしていく。

```python
from google.colab import drive 
from transformers import T5Tokenizer, AutoModelForCausalLM
drive.mount('/content/drive')
%cd '/content/drive/My Drive/Colab Notebooks/'

# load tokenizer
tokenizer = T5Tokenizer.from_pretrained("rinna/japanese-gpt2-medium")
# load fine tuned model
model = AutoModelForCausalLM.from_pretrained("output/")

input = tokenizer.encode("近年人工知能の活用は著しく上昇している。", return_tensors="pt")
output = model.generate(input, do_sample=True, max_length=100, num_return_sequences=8)
print(tokenizer.batch_decode(output)[0])
```

### Output
```
近年人工知能の活用は著しく上昇している。
 人工知能活用で重要なことは、人工知能を正しく理解し、適切な運用をするということである。しかし、人工知能の利用で、実際に何か困ったことが発生した場合、どうすればよいのだろうか。 企業経営者、人事・労務担当者の皆さんは、人工知能に対する高い関心を持っている。また、これまで、人工知能を活用したことがなかったため、不安を抱いている方も多い。そこで、今回、人工知能活用のポイントについてご紹介したい。 最近、企業

```



# 今後の課題
- 推論処理時間の長いmodelをどのようにアプリ実装していくかを検討する必要がある。([WIP](https://github.com/kackey0-1/project_ai))
    - 一つの案としては、非同期処理にて処理をすることを考えている。その時にはWebサービスを提供しているサーバーとは別のバックエンドサービスを用意して、別のサーバーで処理させることでアプリケーションサービスへの影響がなくサービスを提供することができると思う。
- 推論の精度を上げるためのデータセットの収集がキーになる。
    - 無料&ライセンスフリーのWeb記事を収集してカテゴリごとにモデルを作成していくことがいいのかなと考えている。

# 参照元
[Pre-Trained Model **rinna/japanese-gpt2-medium**](https://huggingface.co/rinna/japanese-gpt2-medium)