Word2Vec实现文本识别分类

news/2025/2/13 5:55:37/

深度学习训练营之使用Word2Vec实现文本识别分类

  • 原文链接
  • 环境介绍
  • 前言
  • 前置工作
    • 设置GPU
    • 数据查看
    • 构建数据迭代器
  • Word2Vec的调用
  • 生成数据批次和迭代器
  • 模型训练
    • 初始化
    • 拆分数据集并进行训练
  • 预测

原文链接

  • 🍨 本文为🔗365天深度学习训练营 中的学习记录博客
  • 🍦 参考文章:365天深度学习训练营-第N4周:用Word2Vec实现文本分类
  • 🍖 原作者:K同学啊|接辅导、项目定制

环境介绍

  • 语言环境:Python3.9.12
  • 编译器:jupyter notebook
  • 深度学习环境:TensorFlow2

前言

本次内容我本来是使用miniconda的环境的,但是好像有文件发生了损坏,出现了如下报错,据我所了解应该是某个文件发生了损坏,应该是之前将anaconda误删有关,有所了解或者有同样问题的朋友可以一起进行探讨

前置工作

设置GPU

如果

# 先进行数据加载
import torch
import torch.nn as nn
import torchvision
import os,PIL,pathlib,warnings
import time
from torchvision import transforms, datasets
from torch import nn
from torch.utils.data.dataset import random_splitwarnings.filterwarnings("ignore")#忽略警告信息
device=torch.device("cuda"if torch.cuda.is_available()else "cpu")
device

device(type=‘cpu’)

数据查看

本次使用的数据集和之前中文文本识别分类的是一样的

import pandas as pd
train_data=pd.read_csv('train.csv',sep='\t',header=None)
train_data.head()

在这里插入图片描述

构建数据迭代器

#构建数据集迭代器
def coustom_data_iter(texts,labels):for x,y in zip(texts,labels):yield x,yx=train_data[0].values[:]
y=train_data[1].values[:]    

添加数据迭代器是为了让数据的随机性增强,进行数据集的划分,可以有效的发挥内存的高利用率

Word2Vec的调用

对Word2Vec进行直接的调用

from gensim.models.word2vec import Word2Vec
import numpy as np
#训练浅层神经网络模型
w2v=Word2Vec(vector_size=100,min_count=3)w2v.build_vocab(x)
w2v.train(x,total_examples=w2v.corpus_count,epochs=30)

build_vocab统计输入每一个词汇出现的次数

def average_vec(text):vec=np.zeros(100).reshape((1,100))#表示平均向量#(n,100),其中n表示x中的元素的数量 for word in text:try:vec+=w2v.wv[word].reshape((1,100))except KeyError:continue#未找到,再进行迭代下一个词return vecx_vec=np.concatenate([average_vec(z) for z in x])
w2v.save('w2v_model.pkl')

该步骤将输入的文本转变成了平均向量
对于输入进来的text当中的每一个单词都进行一个查询,确认是否当中有该词,如果有那么就将其添加到vector当中,否则跳出本层循环,查找下一个词.
最后通过np当中的concatenate方法进行一个向量的连接

train_iter=coustom_data_iter(x_vec,y)#训练迭代器
print(len(x),len(y))

12100 12100

设置训练的迭代器

label_name=list(set(train_data[1].values[:]))
print(label_name)
['FilmTele-Play', 'Weather-Query', 'Audio-Play', 'Radio-Listen', 'HomeAppliance-Control', 'Alarm-Update', 'Travel-Query', 'Video-Play', 'Calendar-Query', 'TVProgram-Play', 'Music-Play', 'Other']

生成数据批次和迭代器

text_pipeline=lambda x:average_vec(x)
label_pipeline=lambda x:label_name.index(x)
#lambda语法:lambda  arguments
text_pipeline("我想你了")

在这里插入图片描述

label_pipeline("Travel-Query")

6

这里的结果每次都会不太一样,具有一定的随机性

from torch.utils.data import DataLoaderdef collate_batch(batch):label_list, text_list= [], []for (_text,_label) in batch:# 标签列表label_list.append(label_pipeline(_label))# 文本列表processed_text = torch.tensor(text_pipeline(_text), dtype=torch.float32)text_list.append(processed_text)# 偏移量,即语句的总词汇量label_list = torch.tensor(label_list, dtype=torch.int64)text_list  = torch.cat(text_list)return text_list.to(device),label_list.to(device)# 数据加载器,调用示例
dataloader = DataLoader(train_iter,batch_size=8,shuffle   =False,collate_fn=collate_batch)

和之前的不同在于没有了offset

模型训练

from torch import nnclass TextClassificationModel(nn.Module):def __init__(self, num_class):super(TextClassificationModel, self).__init__()self.fc = nn.Linear(100, num_class)def forward(self, text):return self.fc(text)

初始化

num_class  = len(label_name)
vocab_size = 100000
em_size    = 12
model      = TextClassificationModel(num_class).to(device)
import timedef train(dataloader):model.train()  # 切换为训练模式total_acc, train_loss, total_count = 0, 0, 0log_interval = 50start_time   = time.time()for idx, (text,label) in enumerate(dataloader):predicted_label = model(text)optimizer.zero_grad()                    # grad属性归零loss = criterion(predicted_label, label) # 计算网络输出和真实值之间的差距,label为真实值loss.backward()                          # 反向传播torch.nn.utils.clip_grad_norm_(model.parameters(), 0.1) # 梯度裁剪optimizer.step()  # 每一步自动更新# 记录acc与losstotal_acc   += (predicted_label.argmax(1) == label).sum().item()train_loss  += loss.item()total_count += label.size(0)if idx % log_interval == 0 and idx > 0:elapsed = time.time() - start_timeprint('| epoch {:1d} | {:4d}/{:4d} batches ''| train_acc {:4.3f} train_loss {:4.5f}'.format(epoch, idx, len(dataloader),total_acc/total_count, train_loss/total_count))total_acc, train_loss, total_count = 0, 0, 0start_time = time.time()def evaluate(dataloader):model.eval()  # 切换为测试模式total_acc, train_loss, total_count = 0, 0, 0with torch.no_grad():for idx, (text,label) in enumerate(dataloader):predicted_label = model(text)loss = criterion(predicted_label, label)  # 计算loss值# 记录测试数据total_acc   += (predicted_label.argmax(1) == label).sum().item()train_loss  += loss.item()total_count += label.size(0)return total_acc/total_count, train_loss/total_count

拆分数据集并进行训练

from torch.utils.data.dataset import random_split
from torchtext.data.functional import to_map_style_dataset
# 超参数
EPOCHS     = 30 # epoch
LR         = 5  # 学习率
BATCH_SIZE = 64 # batch size for trainingcriterion = torch.nn.CrossEntropyLoss()
optimizer = torch.optim.SGD(model.parameters(), lr=LR)
scheduler = torch.optim.lr_scheduler.StepLR(optimizer, 1.0, gamma=0.1)
total_accu = None# 构建数据集
train_iter = coustom_data_iter(train_data[0].values[:], train_data[1].values[:])
train_dataset = to_map_style_dataset(train_iter)split_train_, split_valid_ = random_split(train_dataset,[int(len(train_dataset)*0.8),int(len(train_dataset)*0.2)])train_dataloader = DataLoader(split_train_, batch_size=BATCH_SIZE,shuffle=True, collate_fn=collate_batch)valid_dataloader = DataLoader(split_valid_, batch_size=BATCH_SIZE,shuffle=True, collate_fn=collate_batch)for epoch in range(1, EPOCHS + 1):epoch_start_time = time.time()train(train_dataloader)val_acc, val_loss = evaluate(valid_dataloader)# 获取当前的学习率lr = optimizer.state_dict()['param_groups'][0]['lr']if total_accu is not None and total_accu > val_acc:scheduler.step()else:total_accu = val_accprint('-' * 69)print('| epoch {:1d} | time: {:4.2f}s | ''valid_acc {:4.3f} valid_loss {:4.3f} | lr {:4.6f}'.format(epoch,time.time() - epoch_start_time,val_acc,val_loss,lr))print('-' * 69)
| epoch 1 |   50/ 152 batches | train_acc 0.742 train_loss 0.02635
| epoch 1 |  100/ 152 batches | train_acc 0.820 train_loss 0.02033
| epoch 1 |  150/ 152 batches | train_acc 0.838 train_loss 0.01927
---------------------------------------------------------------------
| epoch 1 | time: 0.95s | valid_acc 0.819 valid_loss 0.023 | lr 5.000000
---------------------------------------------------------------------
| epoch 2 |   50/ 152 batches | train_acc 0.850 train_loss 0.01876
| epoch 2 |  100/ 152 batches | train_acc 0.849 train_loss 0.02012
| epoch 2 |  150/ 152 batches | train_acc 0.847 train_loss 0.01736
---------------------------------------------------------------------
| epoch 2 | time: 0.92s | valid_acc 0.869 valid_loss 0.016 | lr 5.000000
---------------------------------------------------------------------
| epoch 3 |   50/ 152 batches | train_acc 0.858 train_loss 0.01588
| epoch 3 |  100/ 152 batches | train_acc 0.833 train_loss 0.02008
| epoch 3 |  150/ 152 batches | train_acc 0.864 train_loss 0.01813
---------------------------------------------------------------------
| epoch 3 | time: 0.86s | valid_acc 0.835 valid_loss 0.023 | lr 5.000000
---------------------------------------------------------------------
| epoch 4 |   50/ 152 batches | train_acc 0.883 train_loss 0.01309
| epoch 4 |  100/ 152 batches | train_acc 0.899 train_loss 0.00996
| epoch 4 |  150/ 152 batches | train_acc 0.895 train_loss 0.00927
---------------------------------------------------------------------
| epoch 4 | time: 0.87s | valid_acc 0.888 valid_loss 0.011 | lr 0.500000
---------------------------------------------------------------------
| epoch 5 |   50/ 152 batches | train_acc 0.906 train_loss 0.00834
...
| epoch 30 |  150/ 152 batches | train_acc 0.900 train_loss 0.00717
---------------------------------------------------------------------
| epoch 30 | time: 0.92s | valid_acc 0.886 valid_loss 0.010 | lr 0.000000
---------------------------------------------------------------------
test_acc, test_loss = evaluate(valid_dataloader)
print('test accuracy {:8.3f}'.format(test_acc))

在这里插入图片描述

预测

def predict(text, text_pipeline):with torch.no_grad():text = torch.tensor(text_pipeline(text),dtype=torch.float32)print(text.shape)output = model(text)return output.argmax(1).item()ex_text_str = "随便播放一首专辑阁楼里的佛里的歌"
#ex_text_str = "还有双鸭山到淮阴的汽车票吗13号的"
model = model.to(device)print("该文本的类别是:%s" % label_name[predict(ex_text_str, text_pipeline)])
torch.Size([1, 100])
该文本的类别是:Music-Play

http://www.ppmy.cn/news/880783.html

相关文章

UE4 关于使用Webbrowser插件遇到的问题以及解决办法

1.无法播放网页视频,这是因为UE4的WebBrowser自带的cef3为3071版本,默认不支持h264等直播流,导致web里的直播流无法播放 解决办法:第一种办法,重新编译了cef源码,改成支持H.264,然后在UE4安装目…

如何破解PDF文件密码(在线破解PDF密码)

如何破解PDF文件密码(在线破解PDF密码) fcwgw.5d6d.com 整理:凌空飞度社区 每当毕业临近的时候,毕业生都会忙着写论文,每逢此时,Adobe Reader就是最忙的了,但是有时候遇到一些加密的PDF文档,Adobe Reader也没辙。 今…

PDF转Word的时候需要输入密码怎么办?

平时查看PDF的时候明明PDF文档可以正常打开,但却无法转换而且提示要输入密码,这是怎么回事呢?出现这种情况一般是PDF设置了安全性加密,禁止转换或编辑等操作,我们只需要解密就能正常转换啦。我有个方法,简单…

如何给PDF设置打开密码?这2种免费方法很实用

如今PDF目前是很多公司最常用的文档格式,有些资料仅供内部传阅,并不希望被其他人看到,为了防止被泄露,经常给PDF文档添加密码,那么有哪些免费的方法可以给PDF设置打开密码呢? 方式1:编辑器加密…

打开PDF文件的密码忘记了

忘记了PDF文件的打开密码,导致无法打开文件,这就是加密文件带来的弊端,不过大家在加密的时候能够记住密码或者设置自己经常使用的密码,这样就不会出现不能打开文件的情况,可是如果忘记了密码还想打开文件。那就需要使用…

pdf怎么加密码怎么设置密码?

pdf怎么加密码怎么设置密码?为什么要给pdf文件加密码呢?因为我们都习惯用pdf文件来编写重要的文件,那么文件内容的安全性就必须要考虑,防止文件内容的泄漏就成了重要的问题,最简单又比较实用的解决办法就是设置密码&am…

PDF文件打开密码如何解密

PDF文件设置了打开密码,可以保护文件内容,有效控制查看文件人数等,但是网上下载的PDF文件也带有打开密码就给我们带来了一些麻烦,想要打开PDF文件,需要解密PDF文件的打开密码。想要解密PDF文件需要使用解密软件&#x…

怎么把PDF加密?这3种方法让你轻松给PDF文件加密

现在我们的工作、学习和生活中,常会用到办公软件,其中PDF因为不易编辑,传输效果好,可以加密等特点深受大家的喜爱。我作为一个职场人,在需要分享PDF文件到人数比较多的平台时,为了不让其他人可以随意地查看…