神经网络语言模型(NNLM)

这篇具有很好参考价值的文章主要介绍了神经网络语言模型(NNLM)。希望对大家有所帮助。如果存在错误或未考虑完全的地方,请大家不吝赐教,您也可以点击"举报违法"按钮提交疑问。

1 为什么使用神经网络模型?

  • 解决独热编码无法解决词之间相似性问题
    • 使用神经网络语言模型中出现的词向量 C w i C_{wi} Cwi代替
    • C w i C_{wi} Cwi就是单词对应的 Word Embedding【词向量】
  • 解决独热编码占用内存较大的问题

2 什么是神经网络模型?

神经网络语言模型(NNLM)

  • Q矩阵相关参数

    • Q矩阵:从one-hot编码生成新的词向量
    • Q矩阵是参数,需要学习训练,刚开始用随机值初始化 Q矩阵,当这个网络训练好之后,Q矩阵的内容被正确赋值,每一行代表一个单词对应的 Word embedding
      参数 含义
      Q Q Q V ∗ m V*m Vm的矩阵,模型参数
      V V V 词典大小,词的个数,有几个词就有几行
      m m m 新词向量的大小

    神经网络语言模型(NNLM)

  • 神经网络相关参数

    参数 含义
    W W W word缩写,表示单词
    t t t target缩写,表示目标词【标签词】
    n n n 窗口大小,上下文的大小(即周围的单词有多少个)称为窗口大小
    C C C 就是Q 矩阵,需要学习的参数函数

神经网络语言模型(NNLM)

  • 举例:
    • 文本You say goodbye and I say hello

      单词 index
      You 0
      say 1
      goodbye 2
      and 3
      I 4
      hello 5
    • 窗口大小n=2,t从2开始,下标从0开始

      contexts target contexts index target index
      [You ,say] [goodbye] [0,1] [2]
      [say ,goodbye] [and ] [1,2] [3]
      [goodbye, and] [I] [2,3] [4]
      [and, I] [say ] [3,4] [1]
      [I ,say] [hello] [4,1] [5]

3. 代码实现

3.1 语料库预处理代码

def preprocess(sentences_list,lis=[]):
   """
      语料库预处理

      :param text_list:句子列表
      :return:
           word_list 是单词列表
           word_dict:是单词到单词 ID 的字典
           number_dict 是单词 ID 到单词的字典
           n_class 单词数
   """
   for i in sentences_list:
       text = i.split(' ')  # 按照空格分词,统计 sentences的分词的个数
       word_list = list({}.fromkeys(text).keys())  # 去重 统计词典个数
       lis=lis+word_list
   word_list=list({}.fromkeys(lis).keys())
   word_dict = {w: i for i, w in enumerate(word_list)}
   number_dict = {i: w for i, w in enumerate(word_list)}
   n_class = len(word_dict)  # 词典的个数,也是softmax 最终分类的个数
   return word_list, word_dict, number_dict,n_class

神经网络语言模型(NNLM)

3.2 词向量创建

def make_batch(sentences_list, word_dict, windows_size):
    """
    词向量编码函数

    :param sentences_list:句子列表
    :param word_dict: 字典{'You': 0,,,} key:单词,value:索引
    :param windows_size: 窗口大小
    :return:
        input_batch:数据集向量
        target_batch:标签值
    """
    input_batch, target_batch = [], []
    for sen in sentences_list:
        word_repeat_list = sen.split(' ')  # 按照空格分词
        for i in range(windows_size, len(word_repeat_list)):  # 目标词索引迭代
            target = word_repeat_list[i]  # 获取目标词
            input_index = [word_dict[word_repeat_list[j]] for j in range((i - windows_size), i)]  # 获取目标词相关输入数据集
            target_index = word_dict[target]  # 目标词索引
            input_batch.append(input_index)
            target_batch.append(target_index)

    return input_batch, target_batch

神经网络语言模型(NNLM)

3.3 NNLM模型类

# Model
class NNLM(nn.Module):
    def __init__(self):
        super(NNLM, self).__init__()
        self.C = nn.Embedding(n_class, m)  # 矩阵Q  (V x m)  V 表示word的字典大小, m 表示词向量的维度
        self.H = nn.Linear(windows_size * m, n_hidden, bias=False)  #
        self.d = nn.Parameter(torch.ones(n_hidden))
        self.U = nn.Linear(n_hidden, n_class, bias=False)
        self.W = nn.Linear(windows_size * m, n_class, bias=False)
        self.b = nn.Parameter(torch.ones(n_class))

    def forward(self, X):
        X = self.C(X)  # X : [batch_size, n_step, m]
        X = X.view(-1, windows_size * m)  # [batch_size, n_step * m]
        tanh = torch.tanh(self.d + self.H(X))  # [batch_size, n_hidden]
        output = self.b + self.W(X) + self.U(tanh)  # [batch_size, n_class]
        return output

3.4 完整代码

import torch
import torch.nn as nn
import torch.optim as optim


def preprocess(sentences_list,lis=[]):
    """
       语料库预处理

       :param text_list:句子列表
       :return:
            word_list 是单词列表
            word_dict:是单词到单词 ID 的字典
            number_dict 是单词 ID 到单词的字典
            n_class 单词数
    """
    for i in sentences_list:
        text = i.split(' ')  # 按照空格分词,统计 sentences的分词的个数
        word_list = list({}.fromkeys(text).keys())  # 去重 统计词典个数
        lis=lis+word_list
    word_list=list({}.fromkeys(lis).keys())
    word_dict = {w: i for i, w in enumerate(word_list)}
    number_dict = {i: w for i, w in enumerate(word_list)}
    n_class = len(word_dict)  # 词典的个数,也是softmax 最终分类的个数
    return word_list, word_dict, number_dict,n_class

def make_batch(sentences_list, word_dict, windows_size):
    """
    词向量编码函数

    :param sentences_list:句子列表
    :param word_dict: 字典{'You': 0,,,} key:单词,value:索引
    :param windows_size: 窗口大小
    :return:
        input_batch:数据集向量
        target_batch:标签值
    """
    input_batch, target_batch = [], []
    for sen in sentences_list:
        word_repeat_list = sen.split(' ')  # 按照空格分词
        for i in range(windows_size, len(word_repeat_list)):  # 目标词索引迭代
            target = word_repeat_list[i]  # 获取目标词
            input_index = [word_dict[word_repeat_list[j]] for j in range((i - windows_size), i)]  # 获取目标词相关输入数据集
            target_index = word_dict[target]  # 目标词索引
            input_batch.append(input_index)
            target_batch.append(target_index)

    return input_batch, target_batch

# Model
class NNLM(nn.Module):
    def __init__(self):
        super(NNLM, self).__init__()
        self.C = nn.Embedding(n_class, m)  # 矩阵Q  (V x m)  V 表示word的字典大小, m 表示词向量的维度
        self.H = nn.Linear(windows_size * m, n_hidden, bias=False)  #
        self.d = nn.Parameter(torch.ones(n_hidden))
        self.U = nn.Linear(n_hidden, n_class, bias=False)
        self.W = nn.Linear(windows_size * m, n_class, bias=False)
        self.b = nn.Parameter(torch.ones(n_class))

    def forward(self, X):
        X = self.C(X)  # X : [batch_size, n_step, m]
        X = X.view(-1, windows_size * m)  # [batch_size, n_step * m]
        tanh = torch.tanh(self.d + self.H(X))  # [batch_size, n_hidden]
        output = self.b + self.W(X) + self.U(tanh)  # [batch_size, n_class]
        return output
if __name__ == '__main__':
    m = 2  # 词向量的维度
    n_hidden = 2  # 隐层个数
    windows_size = 2
    sentences_list = ['You say goodbye and I say hello']  # 训练数据
    word_list, word_dict, number_dict,n_class=preprocess(sentences_list)
    print('word_list为: ',word_list)
    print('word_dict为:',word_dict)
    print('number_dict为:',number_dict)
    print('n_class为:',n_class)
    #
    input_batch, target_batch = make_batch(sentences_list, word_dict, windows_size)  # 构建输入数据和 target label
    # # 转为 tensor 形式
    input_batch,target_batch = torch.LongTensor(input_batch), torch.LongTensor(target_batch)
    print(input_batch)
    print(target_batch)
    model = NNLM()
    # 损失函数定义
    criterion = nn.CrossEntropyLoss()  # 交叉熵损失函数

    # 采用 Adam 优化算法 学习率定义为   0.001
    optimizer = optim.Adam(model.parameters(), lr=0.001)
    # Training 迭代 2000次
    for epoch in range(2000):
        optimizer.zero_grad()  # 梯度归零
        output = model(input_batch)

        # output : [batch_size, n_class], target_batch : [batch_size]
        loss = criterion(output, target_batch)
        if (epoch + 1) % 250 == 0:
            print('Epoch:', '%d' % (epoch + 1), 'cost =', '{:.6f}'.format(loss))
        loss.backward()  # 反向传播计算 每个参数的梯度值
        optimizer.step()  # 每一个参数的梯度值更新

    # Predict
    predict = model(input_batch).data.max(1, keepdim=True)[1]
    print(list(predict))
    # Test
    print([number_dict[n.item()] for n in predict.squeeze()])

神经网络语言模型(NNLM)文章来源地址https://www.toymoban.com/news/detail-437554.html

到了这里,关于神经网络语言模型(NNLM)的文章就介绍完了。如果您还想了解更多内容,请在右上角搜索TOY模板网以前的文章或继续浏览下面的相关文章,希望大家以后多多支持TOY模板网!

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处: 如若内容造成侵权/违法违规/事实不符,请点击违法举报进行投诉反馈,一经查实,立即删除!

领支付宝红包 赞助服务器费用

相关文章

觉得文章有用就打赏一下文章作者

支付宝扫一扫打赏

博客赞助

微信扫一扫打赏

请作者喝杯咖啡吧~博客赞助

支付宝扫一扫领取红包,优惠每天领

二维码1

领取红包

二维码2

领红包