【自然语言处理】(2) --Word2Vec实现

文章目录

  • Word2Vec实现
    • 一、训练模型
      • [1. 数据预处理](#1. 数据预处理)
      • [2. 构建训练数据](#2. 构建训练数据)
      • [3. 搭建word2vec网络(CBOW)](#3. 搭建word2vec网络(CBOW))
      • [4. 装配设备](#4. 装配设备)
      • [5. 构建训练模型](#5. 构建训练模型)
      • [6. 优化器](#6. 优化器)
      • [7. 损失函数](#7. 损失函数)
      • [8. 迭代模型](#8. 迭代模型)
    • 二、测试模型
      • [1. 预测单词](#1. 预测单词)
      • [2. 生成词嵌入词典](#2. 生成词嵌入词典)
      • [3. 保存训练后的词向量](#3. 保存训练后的词向量)
  • 总结

Word2Vec实现

Word2Vec 是一种用于自然语言处理(NLP)的深度学习技术,主要用于将词汇表中的单词或短语从词汇空间映射到向量的实数空间 ,这些向量通常称为词向量(word vectors)。生成的词向量能够捕捉单词之间的语义和语法关系,极大地促进了 NLP 任务的性能和准确性。

一、训练模型

1. 数据预处理

对语料库进行去重(利用集合的特性,进行去重),然后对每个单词进行编号:

python 复制代码
"""-----语料库去重-----"""
CONTEXT_SIZE = 2 # 设置词左边和右边选择的个数
raw_text = """We are about to study the idea of a computational process.
Computational processes are abstract beings that inhabit computers.
As they evolve, processes manipulate other abstract things called data.
The evolution of a process is directed by a pattern of rules
called a program. People create programs to direct processes. In effect,
we conjure the spirits of the computer with our spells.""".split()

vocab = set(raw_text) # 将列表转化为集合,去重
vocab_size = len(vocab)

"""-----对每个单词编号-----"""
# for循环的复合写法,第一次循环,i得到的索引号,word得到第1个单词
word_to_idx = {word:i for i,word in enumerate(vocab)}
idx_to_word = {i:word for i,word in enumerate(vocab)}

2. 构建训练数据

将每个中心词的前两个与后两个词放在一起作为特征将中心词作为标签

python 复制代码
data = [] # 获取上下文词,将上下文词作为输入,目标词作为输出,构建训练数据集
for i in range(CONTEXT_SIZE,len(raw_text) - CONTEXT_SIZE):
    context = (
        [raw_text[i - (2-j)] for j in range(CONTEXT_SIZE)] # [we,are]
        + [raw_text[i + j + 1] for j in range(CONTEXT_SIZE)] # [to,study]
    ) # 元组,获取上下文词(['we','are','to','study'])
    target = raw_text[i] # 获取目标词'about'
    data.append((context,target)) # 将上下文词和目标词保存到data中[((['we','are','to','study']),'about')]

def make_context_vector(context,word_to_ix):
    idxs = [word_to_ix[w] for w in context]
    return torch.tensor(idxs,dtype=torch.long)

print(make_context_vector(data[0][0],word_to_idx))
-------------
tensor([22,  9, 31, 30])

3. 搭建word2vec网络(CBOW)

python 复制代码
class CBOW(nn.Module):
    def __init__(self,vocab_size,embedding_dim):
        super(CBOW,self).__init__()
        self.embedding = nn.Embedding(vocab_size,embedding_dim) # 词嵌入层,得到词向量信息
        self.proj = nn.Linear(embedding_dim,128)
        self.output = nn.Linear(128,vocab_size)

    def forward(self,inputs):
        embeds = sum(self.embedding(inputs)).view(1,-1)
        out = F.relu(self.proj(embeds))
        out = self.output(out)
        nll_prob = F.log_softmax(out,dim=-1)
        return nll_prob

4. 装配设备

python 复制代码
# 模拟在cuda训练
device = "cuda" if torch.cuda.is_available() else "mps" if torch.backends.mps.is_available() else "cpu"
print(device)
-----------
cuda

5. 构建训练模型

python 复制代码
model = CBOW(vocab_size,10).to(device)

6. 优化器

python 复制代码
optimizer = optim.Adam(model.parameters(),lr=0.001)

7. 损失函数

NLLLoss损失函数(当分类列表比较多的情况),将多个类别分别分成0,1两个类别:

python 复制代码
"""-----损失函数-----"""
losses = [] # 存储损失的集合
loss_function = nn.NLLLoss() # NLLLoss损失函数(当分类列表比较多的情况),将多个类别分别分成0,1两个类别

8. 迭代模型

python 复制代码
"""-----迭代模型参数权重-----"""
for epoch in tqdm(range(200)):
    total_loss = 0
    for context,target in data:
        context_vector = make_context_vector(context,word_to_idx).to(device)
        target = torch.tensor([word_to_idx[target]]).to(device)
        # 开始前向传播
        train_predict = model(context_vector)
        loss = loss_function(train_predict,target)
        # 反向传播
        optimizer.zero_grad() # 梯度值清零
        loss.backward() # 反向传播计算得到每个参数的梯度值
        optimizer.step()# 根据梯度更新网络参数

        total_loss += loss.item()
    losses.append(total_loss)
----------------------
100%|██████████| 200/200 [00:24<00:00,  8.11it/s]

二、测试模型

1. 预测单词

python 复制代码
"""-----测试-----"""
context = ['process','is','by','a']
context_vector = make_context_vector(context,word_to_idx).to(device)

# 预测的值
model.eval() # 进入测试模式
predict = model(context_vector)
max_idx = predict.argmax(1)

# 预测的单词
keys = [key for key, value in word_to_idx.items() if value == max_idx]
print("process is by a中间的是"," ".join(keys))
----------------
process is by a中间的是 directed

2. 生成词嵌入词典

获取每个词的词向量,将对应的词同词向量一一对应以字典类型存放:

python 复制代码
"""-----生成词嵌入字典-----"""
# 获取词向量,这个Embedding就是我们需要的词向量,他只是一个模型的中间过程
print("CBOW embedding'weight = ",model.embedding.weight)
w = model.embedding.weight.cpu().detach().numpy()
print(w)

word_2_vec = {}
for word in word_to_idx.keys():
    # 词向量矩阵中某个词的索引所对应的那一列即为该词的词向量
    word_2_vec[word] = w[word_to_idx[word],:]
print('结束')

3. 保存训练后的词向量

训练后的词向量保存为npz文件:npz文件是numpy库中的一种数据格式,它是一种压缩文件,可以保存多个数组和元数据。

  • 保存方法:
python 复制代码
np.savez("文件名称格式",文件)
  • 调用方法:
python 复制代码
data = np.load("文件名")
python 复制代码
np.savez("word2vec实现.npz",file_1=w)
data = np.load("word2vec实现.npz")
print(data.files)
------------
['file_1']

总结

本篇介绍了:

  1. 如何实现Word2Vec,从而搭建网络模型进行对词的预测。
  2. 生成词典:将每个单词同它对应的词向量在字典中存放在一起。
  3. 保存训练好的词典:将生成好的词典,保存进.npz文件中。
相关推荐
dundunmm19 分钟前
数据挖掘之认识数据
人工智能·机器学习·信息可视化·数据挖掘
FBI780980459439 分钟前
API接口在电商行业中的创新应用与趋势
运维·网络·人工智能·爬虫·python
Sword9942 分钟前
豆包 MarsCode AI Apply功能揭秘:自动代码应用与 Diff 实现
前端·人工智能·豆包marscode
梁小憨憨43 分钟前
机器学习(Machine Learning)的安全问题
人工智能·安全·机器学习
Gauss松鼠会1 小时前
GaussDB数据库中SQL诊断解析之配置SQL限流
数据库·人工智能·sql·mysql·gaussdb
愚者大大2 小时前
1. 深度学习介绍
人工智能·深度学习
liuming19922 小时前
Halcon中histo_2dim(Operator)算子原理及应用详解
图像处理·人工智能·深度学习·算法·机器学习·计算机视觉·视觉检测
聆思科技AI芯片2 小时前
实操给桌面机器人加上超拟人音色
人工智能·机器人·大模型·aigc·多模态·智能音箱·语音交互
海棠AI实验室2 小时前
机器学习基础算法 (一)-线性回归
人工智能·python·机器学习