ch.7 RNNを使用した文の作成


言語モデルを使用して文を生成する



T個のテーブル列データを一度に処理する層
  • Time Embedding階層化:単語IDを単語に変換する分散表現
  • Time LSTM層:RNNとは異なり、C(メモリセル)はLSTM層のみで使用され、ゲートウェイ(出力、忘れ、入力、メモリセル(非ゲートウェイ)
  • が追加する.
  • Time Affineレイヤ:LSTM経由の非表示状態
  • を入力.
  • Time Softmaxレイヤ:出力
  • の確率分布
    「You saygoodbye and I sayhello」で学習後I入力

    このように,Softmax層ではI以降の正しい単語を確率分布として出力する.
    文を生成するモデルを作成するには、次の単語として適切な単語を選択し、その単語を言語モデルに再入力し、適切な単語を出力して繰り返します.
  • 確率選択
    Softmax出力の確率分布による確率選択
    生成文は、実行ごとに異なる場合があります.
  • 決定的選択
    確率分布で最も確率の高い単語を選択
    実行ごとに同じ文
  • が生成される.

    この過程を繰り返す
    任意の回数または終端記号などに遭遇するまで.
  • の意味:生成された文は既存の文ではなく、新しく生成された文である.トレーニングデータを暗記するのではなく、トレーニングデータの単語ソートパターン、ルールを学習しました.
  • ここで文章を勉強すると、単語の順序や個数が変わっただけだと思うかもしれませんが、より大きな語彙量を勉強すると、より豊かな表現と文が得られます.
    class RnnlmGen(Rnnlm): # Rnnlm 클래스 상속
      # generate: 문장 생성을 수행하는 메서드
      def generate(self, start_id, skip_ids=None, sample_size = 100):
        word_ids = [start_id]
    
        x = start_id
        while(len(word_ids) < sample_size):
          x = np.array(x).reshape(1, 1) # x는 이차원 배열(predict가 미니배치 처리를 해서)
          score = self.predict(x) # 전처리 이전
          p = softmax(score.flatten())
    
          sampled = np.random.choice(len(p), size=1, p=p) # 확률 고려하여 단어 선택
          # 네거티브 샘플링
          if(skip_ids is None) or (sampled not in skip_ids):
            # <unk>, N 등 전처리된 단어 샘플링하지 않도록
            # <unk>: 희소한 단어 N: 숫자 <eos>: 문장 구분 기호
            x = sampled
            word_ids.append(int(x))
    
        return word_ids
        
    前述のように、ch.5で作成したRNLMクラスを継承し、言語生成クラスを作成した.
    スタートワードとして「you」を入力するとどのような文が現れるか見てみましょう
    from dataset import ptb
    
    corpus, word_to_id, id_to_word = ptb.load_data('train')
    vocab_size = len(word_to_id)
    corpus_size = len(corpus)
    
    model = RnnlmGen()
    #model.load_params('ch06/Rnnlm.pkl')
    
    #시작 문자, skip 문자 설정
    start_word = 'you'
    start_id = word_to_id[start_word]
    skip_words = ['N', '<unk>', '$']
    skip_ids = [word_to_id[w] for w in skip_words]
    
    # 문장 생성
    word_ids = model.generate(start_id, skip_ids)
    txt = ' '.join([id_to_word[i] for i in word_ids])
    # join: 리스트의 단어들 합쳐줌
    txt = txt.replace(' <eos>', '.\n')
    # 종결 기호를 .\n으로 바꾸어줌
    print(txt)
    
    paramコメントを解除すると学習に設定された重み付け値が反映されたときに文が生成されますが、それよりもスムーズで自然です
    you suspect because of a fund that was slowing to the pace of a smaller pay loans.
    former richard w. really to hastily door to a major man 's cast came a hat of the first time.
    this are widely even complex of half the national intelligence committee are times by the new york judge once out.
    it was considering out said in a tower meeting.
    mr. bush is n't the aides said.
    he warned that he was too convinced.
    in the judge was u.s. activities as stability fees through this year was demanded
    これらの文章を出した.
    今回はch.6で作成したBetterrnnlmを使って文を生成
    class BetterRnnlmGen(BetterRnnlm): # BetterRnnlm 클래스 상속
     # generate: 문장 생성을 수행하는 메서드
     def generate(self, start_id, skip_ids=None, sample_size = 100):
       word_ids = [start_id]
    
       x = start_id
       while(len(word_ids) < sample_size):
         x = np.array(x).reshape(1, 1) # x는 이차원 배열(predict가 미니배치 처리를 해서)
         score = self.predict(x) # 전처리 이전
         p = softmax(score.flatten())
    
         sampled = np.random.choice(len(p), size=1, p=p) # 확률 고려하여 단어 선택
         # 네거티브 샘플링
         if(skip_ids is None) or (sampled not in skip_ids):
           # <unk>, N 등 전처리된 단어 샘플링하지 않도록
           # <unk>: 희소한 단어 N: 숫자 <eos>: 문장 구분 기호
           x = sampled
           word_ids.append(int(x))
    
       return word_ids
    you like to consider new york and reporters care in the problem.
    mr. roman said the fate mr. pediatric says i remember much of those loans about one of the local interbank required even again.
    mr. bergsma sent down slightly to a jury he took over the committee and will meet its warning to a criminal contract.
    but mr. honecker has about taxes.
    mr. stone the top meeting mr. stone played the secretary of mr. freeman.
    in his reputation game mr. senator already is entering individual and the potential of mr. krenz 's chair.
    最初の文にもs+Vとs+vの形で完璧な文が現れた.もっと滑らかな感じがします.


    meining of lifeが後に印刷されたとき、出てきた内容の中で好きなものを持ってきてください.

    7.2 seq2seq


    テーブル列データを他のテーブル列データに変換する問題を見てみましょう.
    例えば、機械翻訳、音声認識、微信機などです.機械翻訳では,自然言語文が入ってきたら,それを解釈し,他の言語の自然言語文を表列データに変換する過程である.
    seq 2 seq:2個のRNNのEncoder-Decoderモデル

    Encoder,Decoder使用RNN!

    Encoder


    エンコーディング:エンコーディング-特定のルールに従って情報を変換
    ex) 'A' -> 1000001

    この図では、エンコーダは、LSTM層を介してh(暗黙の状態ベクトル)を返し、入力文の翻訳および変換に必要な情報を符号化する

    この図から,hは固定長ベクトルであることがわかる.したがって,入力文の長さが異なっていても,同じ長さのhが出力される.

    Decoder


    復号化:復号化:符号化された情報を元の情報に変換
    ex) 1000001 -> 'A'

    形態はよく知られており,前の文生成モデルと似ている.
    初めて区切り文字を入力したときに翻訳すると、韓国語の入力文が英語で1つずつ出力されているのがわかります.
    異なる点は、LSTM層にhを入力することである.
    このhはエンコーダからの非表示状態ベクトルhである.

    レイヤー全体



    階層全体が一目瞭然だ.
    左側はEncoder,右側はDecoderであり,これらRNN中のLSTMからなる.
    ここでhは両者をつなぐ「架橋」の役割を果たす.純粋な伝播では、エンコーダの非表示状態がDecoderに渡され、ファイルを反転するとDecoderからEncoderへの重み付けまたは傾きが渡されます.

    おもちゃの問題(toy problem)


    これまで分かってきたseq 2 seqにより,簡単な自然言語処理問題を解決する.

    このように文字列としてプラス記号演算を入力すると、正しい答えがあるかどうかをチェックします.ここで重要なのは,コンピュータが文字列として入力する+の論理的意味を知らないことである.
    print(12+34)のようにPythonで書くと、すぐに加算します.
    「12+34」文字列の認識が一致しません.最終的には、コンピュータは大量のデータで学習し、文字の法則を把握する必要があります.

    可変長クロック列データ


    このおもちゃの問題では、データは単語ではなく文字で区切られています.
    ex) "12+34"-> ['1','2','+','3','4']
    このとき,問題と答えの長さは桁数によって異なる.すなわち,各サンプルのデータの時間方向の大きさが異なる.小規模学習を行う場合、サンプルのデータ長や形状が同じでなければならないため、「パッケージ」

    Padding


    既存のデータに意味のない値を入力して長さを等しくする方法
    この本は空白を埋める.

    この図では、「」は入力と出力を区別する区切り記号で、Decoderに文字列を生成させることができます.
    精度をさらに高めるには、充填のために追加されたスペースが損失の結果に影響しないようにする必要があります.たとえば、Softmax with Lossレイヤにマスク機能を追加する方法があります.

    3つのデータを確認しました.ダウンジャケットはよくできていて、それぞれの文の長さが固定されていることがわかります.
    sequence.pyというモジュールでは,以前CBOWでword to id,id to wordというディック文を返すようにchar to id,id to charを返してchar idを生成し,trainとtestデータに分ける.
    以上