コムドットのヤマト風のTwitterつぶやきを自動生成してみようと思った

# 初めに
[myjlab advent calendar 2022](https://qiita.com/advent-calendar/2022/myjlab)　7日目を担当する3年の浦です。

GPT-3について書こうとしたのですが、昨日[yoshiki495](https://github.com/yoshiki495)にChatGPTについて書かれ絶望の淵にいました、、、

何についてやるか考えたところ、機械学習演習で自然言語処理をしていこうと思います。

下記の動画を参考にしTwitter APIを使用したマルコフ連鎖に挑戦し、コムドットのヤマトになろうと思います。

<iframe width="560" height="315" src="https://www.youtube.com/embed/x5AwzoQgt3E" title="YouTube video player" frameborder="0" allow="accelerometer; autoplay; clipboard-write; encrypted-media; gyroscope; picture-in-picture" allowfullscreen></iframe>



## マルコフ連鎖とは
>マルコフ連鎖（マルコフれんさ、英: Markov chain）とは、確率過程の一種であるマルコフ過程のうち、とりうる状態が離散的（有限または可算）なもの（離散状態マルコフ過程）をいう。また特に、時間が離散的なもの（時刻は添え字で表される）を指すことが多い（他に連続時間マルコフ過程というものもあり、これは時刻が連続である）。マルコフ連鎖は、未来の挙動が現在の値だけで決定され、過去の挙動と無関係である（マルコフ性）。各時刻において起こる状態変化（遷移または推移）に関して、マルコフ連鎖は遷移確率が過去の状態によらず、現在の状態のみによる系列である。特に重要な確率過程として、様々な分野に応用される。
参照元：[Wikipedia](https://ja.wikipedia.org/wiki/%E3%83%9E%E3%83%AB%E3%82%B3%E3%83%95%E9%80%A3%E9%8E%96)

難しくてよくわからない、、、
そこで「マルコフ連鎖　わかりやすくわかりやすく」と検索すると以下の動画を発見！
<iframe width="560" height="315" src="https://www.youtube.com/embed/O3gcOOHO8fg" title="YouTube video player" frameborder="0" allow="accelerometer; autoplay; clipboard-write; encrypted-media; gyroscope; picture-in-picture" allowfullscreen></iframe>

## 環境開発
GoogleColaboratory

## Twitter APIの取得
Twitterのツイートを取得するためにはTwitter API利用申請が必要になります。
申請方法については以下のリンクにわかりやすく書いてあるので参考にしてください。

https://toxublog.com/blog/twitter_api_apply/

## 必要なもの
* Python
* Twitter api
* Janome
* markovify

```
! pip install markovify
! pip install requests requests_oauthlib
! pip install janome
```
## コード

### Twitterの情報取得
最近のヤマトさんのTwitterの情報100件取得していこうと思います。
```
import tweepy

# API情報を記入
BEARER_TOKEN = "xxxxxxxxxxxxxxxx"
API_KEY = "xxxxxxxxxxxxxxxx"
API_SECRET_KEY = "xxxxxxxxxxxxxxxx"
ACCESS_TOKEN = "xxxxxxxxxxxxxxxx"
ACCESS_TOKEN_SECRET = "xxxxxxxxxxxxxxxx"

def twitter_api() -> tweepy.API:
    auth = tweepy.OAuthHandler(API_KEY, API_SECRET_KEY)
    auth.set_access_token(ACCESS_TOKEN, ACCESS_TOKEN_SECRET)
    return tweepy.API(auth)


def get_user_twitter(user_id):
    api = twitter_api()
    tweets = api.user_timeline(id=user_id, count=1)
    yamato_list=[]
    for tweet in tweets:
        yamato_list.append(tweet.text)
    yamato_text = "".join(yamato_list)
    return yamato_text


yamato_text = get_user_twitter('comyamato0515')
```
実行結果は無事に最近のtwitter100件の情報をもってくることができました。
![スクリーンショット 2022-12-07 14.53.18.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2983787/10ef4e56-1f84-8e03-bca5-6a744ee99cdf.png)

### Janome処理

Janome前の正規化としてURLや半角記号、全角記号などを消していこうと思います。
```
from janome.tokenizer import Tokenizer
import re

def format_text(text):
    '''
    MeCabに入れる前のツイートの整形方法例
    '''
    for i in range(10):
        text=re.sub(r'https ://[\w/:%#\$&\?\(\)~\.=\+\-…]+', "", text)
        text=re.sub('RT', "", text)
        text=re.sub(r'[!-~]', "", text)#半角記号,数字,英字
        text=re.sub(r'[︰-＠]', "", text)#全角記号
        text=re.sub(r'[\uFF01-\uFF0F\uFF1A-\uFF20\uFF3B-\uFF40\uFF5B-\uFF65\u3000-\u303F]', r'', text)
        text=re.sub(r'[▲\▼\”\“]', r'', text)

    return text


yamato_text2=format_text(yamato_text)
```
いらない情報を削除することができすっきりしました。
![スクリーンショット 2022-12-07 14.55.13.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2983787/fff6a985-aa7a-5460-c131-972130ff517f.png)

正規化した文章を分かち書きしていこうと思います。
```
def text_split(text):
    
    str_table = str.maketrans({
        
        '。': '',   
        '\n': '。',
        '\r': '',
        '(': '（',
        ')': '）',
        '[': '［',
        ']': '］',
        '"':'”',
        "'":"’",
    })
    text = text.translate(str_table)

    t = Tokenizer()
    tokens = t.tokenize(text, wakati=True)

    splitted_text_list = []

    for i in tokens:
        if i != '。' and i != '！' and i != '？':
            i += ' '
        elif i == '。' or i == '！' or i == '？':
            i = '\n'
        splitted_text_list.append(i)
        splitted_text_str = "".join(splitted_text_list)

    return splitted_text_str


splitted_text_str = text_split(yamato_text)

```
少し変ですが、分かち書きできました。
![スクリーンショット 2022-12-07 15.03.07.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2983787/aaad2acc-7d19-38b3-57bf-9224e7748d9e.png)

### マルコフ連鎖で文章生成
最後にマルコフ連鎖で文章の生成を行います。
```
import markovify

text_model = markovify.NewlineText(splitted_text_str, state_size=2,  well_formed=False)

for _ in range(10):
    sentence = text_model.make_short_sentence(100, 20, tries=100).replace(' ', '')
    print(sentence)
```
実行結果は文章を自動生成することができましたが、ヤマトさん風の文章にはなりませんでした。
![スクリーンショット 2022-12-07 15.04.46.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2983787/b0268bba-3a5e-655e-542a-675f09151842.png)

## おわり
ヤマトさんはリツイートの内容が多いため、ヤマトさんらしい文章にならなかったと推測しました。

ギリギリ間に合いましたが、実力のない私は、半日で記事の題材決めから作成までやるもんではないことがわかりました。
今後は余裕をもって取り掛かろうと思います。