利用WORDAVG模型做文本分类   模型简单 效果号

简单思想就是  将每个词向量在 句子维度进行求平均  可以用avgpool来做平均池化

然后用平均后的向量作为句子向量 进行文本分类

后面我们还会介绍将rnn表示的句子向量进行文本分类

也可以用cnn进行文本分类

我们这篇文章代码和注释  主要是介绍 WORDEMage进行文本分类

"""
准备数据
TorchText中的一个重要概念是Field。Field决定了你的数据会被怎样处理。在我们的情感分类任务中,
我们所需要接触到的数据有文本字符串和两种情感,"pos"或者"neg"。
Field的参数制定了数据会被怎样处理。
我们使用TEXT field来定义如何处理电影评论,使用LABEL field来处理两个情感类别。
我们的TEXT field带有tokenize='spacy',这表示我们会用spaCy tokenizer来tokenize英文句子。
如果我们不特别声明tokenize这个参数,那么默认的分词方法是使用空格。
安装spaCy
pip install -U spacy
python -m spacy download en
LABEL由LabelField定义。这是一种特别的用来处理label的Field。我们后面会解释dtype。
更多关于Fields,参见https://github.com/pytorch/text/blob/master/torchtext/data/field.py
和之前一样,我们会设定random seeds使实验可以复现。
"""
import torch
from torchtext import dataSEED=1234
torch.manual_seed(SEED)
torch.cuda.manual_seed(SEED)
torch.backends.cudnn.deterministic=True
"""
先决定怎么处理数据  Field是决定如何处理数据的
默认进行空格分词
spacy 是根据点进行分词
spaCy是世界上最快的工业级自然语言处理工具。 支持多种自然语言处理基本功能。
官网地址:https://spacy.io/
spaCy主要功能包括分词、词性标注、词干化、命名实体识别、名词短语提取等等。"""
TEXT=data.Field(tokenize='spacy')
LABEL=data.LabelField(dtype=torch.float)"""
TorchText支持很多常见的自然语言处理数据集。
下面的代码会自动下载IMDb数据集,然后分成train/test两个torchtext.datasets类别。
数据被前面的Fields处理。IMDb数据集一共有50000电影评论,每个评论都被标注为正面的或负面的。
"""
from torchtext import datasets
train_data,test_data=datasets.IMDB.splits(TEXT,LABEL)"""
查看每个数据split 有多少条数据
"""
print(f'number of training examples:{len(train_data)}')
print(f"number of  testing examples:{len(test_data)}")
"""
查看一个example  {'text': ['Brilliant', 'adaptation', 'of', 'the', 'novel', 'that', 'made', 'famous', 'the', 'relatives', 'of', 'Chilean', 'President', 'Salvador', 'Allende', '
killed', '.', 'In', 'the', 'environment', 'of', 'a', 'large', 'estate', 'that', 'arises', 'from', 'the', 'ruins', ',', 'becoming', 'a', 'force', 'to', 'abuse', 'and',
'exploitation', 'of', 'outrage', ',', 'a', 'luxury', 'estate', 'for', 'the', 'benefit', 'of', 'the', 'upstart', 'Esteban', 'Trueba', 'and', 'his', 'undeserved',
'family', ',', 'the', 'brilliant', 'Danish', 'director', 'Bille', 'August', 'recreates', ',', 'in', 'micro', ',', 'which', 'at', 'the', 'time', 'would', 'be', 'the',
'process', 'leading', 'to', 'the', 'greatest', 'infamy', 'of', 'his', 'story', 'to', 'the', 'hardened', 'Chilean', 'nation', ',', 'and', 'whose', 'main',
'character', 'would', 'Augusto', 'Pinochet', '(', 'Stephen', 'similarities', 'with', 'it', 'are', 'inevitable', ':', 'recall', ',', 'as', 'an', 'example', ',',
'that', 'image', 'of', 'the', 'senator', 'with', 'dark', 'glasses', 'that', 'makes', 'him', 'the', 'wink', 'to', 'the', 'general', 'to', 'begin', 'making',
'the', 'palace).<br', '/><br', '/>Bille', 'August', 'attends', 'an', 'exceptional', 'cast', 'in', 'the', 'Jeremy', 'protruding', 'Irons', ',', 'whose',
'character', 'changes', 'from', 'arrogance', 'and', 'extreme', 'cruelty', ',', 'the', 'hard', 'lesson', 'that', 'life', 'always', 'brings', 'us', 'to',
'almost', 'force', 'us', 'to', 'change', '.', 'In', 'Esteban', 'fully', 'applies', 'the', 'law', 'of', 'resonance', ',', 'with', 'great', 'wisdom', ',',
'Solomon', 'describes', 'in', 'these', 'words:"The', 'things', 'that', 'freckles', 'are', 'the', 'same', 'punishment', 'that', 'will', 'serve',
'you', '.', '"', '<', 'br', '/><br', '/>Unforgettable', 'Glenn', 'Close', 'playing', 'splint', ',', 'the', 'tainted', 'sister', 'of', 'Stephen', ',',
'whose', 'sin', ',', 'driven', 'by', 'loneliness', ',', 'spiritual', 'and', 'platonic', 'love', 'was', 'the', 'wife', 'of', 'his', 'cruel', 'snowy', '
brother', '.', 'Meryl', 'Streep', 'also', 'brilliant', ',', 'a', 'woman', 'whose', 'name', 'came', 'to', 'him', 'like', 'a', 'glove', 'Clara', '.',
'With', 'telekinetic', 'powers', ',', 'cognitive', 'and', 'mediumistic', ',', 'this', 'hardened', 'woman', ',', 'loyal', 'to', 'his', 'blunt', ',',
'conservative', 'husband', ',', 'is', 'an', 'indicator', 'of', 'character', 'and', 'self', '-', 'control', 'that', 'we', 'wish', 'for', 'ourselves',
'and', 'for', 'all', 'human', 'beings', '.', '<', 'br', '/><br', '/>Every', 'character', 'is', 'a', 'portrait', 'of', 'virtuosity', '(', 'as', 'Blanca',
'worthy', 'rebel', 'leader', 'Pedro', 'Segundo', 'unhappy', '...', ')', 'or', 'a', 'portrait', 'of', 'humiliation', ',', 'like', 'Stephen', 'Jr.', ',',
'the', 'bastard', 'child', 'of', 'Senator', ',', 'who', 'serves', 'as', 'an', 'instrument', 'for', 'the', 'return', 'of', 'the', 'boomerang', '.',
'<', 'br', '/><br', '/>The', 'film', 'moves', 'the', 'bowels', ',', 'we', 'recreated', 'some', 'facts', 'that', 'should', 'not', 'ever', 'be',
'repeated', ',', 'but', 'that', 'absurdly', 'still', 'happen', '(', 'Colombia', 'is', 'a', 'sad', 'example', ')', 'and', 'another', 'reminder', 'that', ',', 'against', 'all', ',',
'life', 'is', 'wonderful', 'because', 'there', 'are', 'always', 'people', 'like', 'Isabel', 'Allende', 'and', 'immortalize', 'just', 'Bille', 'August', '.'], 'label': 'pos'}
"""print(vars(train_data.examples[0]))"""
由于我们现在只有train/test这两个分类,所以我们需要创建一个新的validation set。我们可以使用.split()创建新的分类。
默认的数据分割是 70、30,如果我们声明split_ratio,可以改变split之间的比例,split_ratio=0.8表示80%的数据是训练集,20%是验证集。
我们还声明random_state这个参数,确保我们每次分割的数据集都是一样的。"""
import random
train_data,valid_data=train_data.split(random_state=random.seed(SEED))
#检查一下现在每个部分有多少条数据
print(f'number of training examples:{len(train_data)}')
print(f'number of  validation examples:{len(valid_data)}')
print(f'number if testing examples:{len(test_data)}')"""
下一步我们需要创建 vocabulary 。vocabulary 就是把每个单词一一映射到一个数字。
我们使用最常见的25k个单词来构建我们的单词表,用max_size这个参数可以做到这一点。
所有其他的单词都用<unk>来表示。"""
#TEXT.build_vocab(train_data,max_Size=25000)\
#LABEL.build_vocab(train_data)
#TEXT.build_vocab(train_data,max_size=25000,vectors='glove.6B.100d',unk_init=torch.Tensor.normal_)
TEXT.build_vocab(train_data, max_size=25000, vectors="glove.6B.100d", unk_init=torch.Tensor.normal_)
LABEL.build_vocab(train_data)print(f'unique tokens in TEXT vocabulary:{len(TEXT.vocab)}')
print(f'unique tokens in LABEL vocabulary:{len(LABEL.vocab)}')"""
当我们把句子传进模型的时候,我们是按照一个个 batch 穿进去的,也就是说,
我们一次传入了好几个句子,而且每个batch中的句子必须是相同的长度。为了确保句子的长度相同,TorchText会把短的句子pad到和最长的句子等长。
下面我们来看看训练数据集中最常见的单词。
[('the', 201455), (',', 192552), ('.', 164402), ('a', 108963), ('and', 108649), ('of', 100010), ('to', 92873), ('is', 76046),
('in', 60904), ('I', 54486), ('it', 53405), ('that', 49155),
('"', 43890), ("'s", 43151), ('this', 42454), ('-', 36769), ('/><br', 35511), ('was', 34990), ('as', 30324), ('with', 29691)]
"""
print(TEXT.vocab.freqs.most_commom(20))"""
我们可以直接用 stoi(string to int) 或者 itos (int to string) 来查看我们的单词表。
['<unk>', '<pad>', 'the', ',', '.', 'a', 'and', 'of', 'to', 'is']
"""
print(TEXT.vocab.itos[:10])"""
查看labels。
defaultdict(<function _default_unk_index at 0x7fbec39a79d8>, {'neg': 0, 'pos': 1})
"""
print(LABEL.vocab.stoi)"""
最后一步数据的准备是创建iterators。每个itartion都会返回一个batch的examples。
我们会使用BucketIterator。BucketIterator会把长度差不多的句子放到同一个batch中,确保每个batch中不出现太多的padding。
严格来说,我们这份notebook中的模型代码都有一个问题,也就是我们把<pad>也当做了
模型的输入进行训练。更好的做法是在模型中把由<pad>产生的输出给消除掉。在这节课中我们简单处理,
这个可以  pack_pad处理即可及解决这个问题 稍后我们对模型进行简单的修改  去掉padd的 值
那么就要知道每个句子的长度
直接把<pad>也用作模型输入了。由于<pad>数量不多,模型的效果也不差。
如果我们有GPU,还可以指定每个iteration返回的tensor都在GPU上。
"""
BATCH_SIZE=64
device=torch.device('cuda' if  torch.cuda.is_available() else 'cpu')train_iterator,valid_iterator,test_iterator=data.BucketIterator.splits((train_data,valid_data,test_data),batch_size=BATCH_SIZE,device=device
)"""
Word Averaging模型
我们首先介绍一个简单的Word Averaging模型。这个模型非常简单,
我们把每个单词都通过Embedding层投射成word embedding vector,然后把一句话中的所有word vector做个平均,
就是整个句子的vector表示了。接下来把这个sentence vector传入一个Linear层,做分类即可。
我们使用avg_pool2d来做average pooling。我们的目标是把sentence length那个维度平均成1,然后保留embedding这个维度。
avg_pool2d的kernel size是 (embedded.shape[1], 1),所以句子长度的那个维度会被压扁。
"""
import torch.nn as nn
import torch.nn.functional as Fclass WordAVGModel(nn.Module):def __init__(self,vocab_size,embedding_dim,output_dim,pad_idx):super(WordAVGModel,self).__init__()self.embedding_dim=nn.Embedding(vocab_size,embedding_dim,padding_idx=pad_idx)self.fc=nn.Linear(embedding_dim,output_dim)def forward(self,text):"""text [seten_len,batch_size]>>>[seten_len,batch_Size,emb_dim]"""embedded=self.embedding(text)"""将bacth_size 的维度放在前面[batch_size,seten_len,embed_size] 也可以用transpose"""embedded=embedded.permute(1,0,2)"""沿着seq_len维度 句子进行平均此话  得到句子的平局词向量[batch_size,1,embed_size]>>>[batch_Size,embed_Size]"""pooled=F.avg_pool2d(embedded,(embedded.shape(1),1)).squeeze()"""将平局之后的句子向量放到线性层 进行分类   [batch_Size,embed_Size]>>>[batch_Size,output_Size]"""return self.fc(pooled)"""
定义超参数
初始化模型
"""
INPUT_DIM=len(TEXT.vocab)
EMNEDDING_DIM=100
OUTPUT_DIM=1
PAD_IDX=TEXT.vocab.stoi[TEXT.pad_token]model=WordAVGModel(INPUT_DIM,EMNEDDING_DIM,OUTPUT_DIM,PAD_IDX)def count_parameters(model):return sum(p.numel() for p in model.parameters() if p.requires_grad)print(f'the model has  {count_parameters(model):,} trainable  parameters')"""
将Glove 100维的词向量  作为模型的初始化参数  可以加速的收敛tensor([[-0.1117, -0.4966,  0.1631,  ...,  1.2647, -0.2753, -0.1325],[-0.8555, -0.7208,  1.3755,  ...,  0.0825, -1.1314,  0.3997],[-0.0382, -0.2449,  0.7281,  ..., -0.1459,  0.8278,  0.2706],...,[-0.7244, -0.0186,  0.0996,  ...,  0.0045, -1.0037,  0.6646],[-1.1243,  1.2040, -0.6489,  ..., -0.7526,  0.5711,  1.0081],[ 0.0860,  0.1367,  0.0321,  ..., -0.5542, -0.4557, -0.0382]])
"""
pretrained_embeddings=TEXT.vocab.vectors
model.embedding.weight.data.copy_(pretrained_embeddings)UNK_IDX=TEXT.vocab.stoi[TEXT.unk_token]
"""
初始化模型参数
"""
model.embedding.weight.data[UNK_IDX]=torch.zeros(EMNEDDING_DIM)
model.embedding.weight.data[PAD_IDX]=torch.zeros(EMNEDDING_DIM)"""
训练模型
"""
import torch.optim as optimoptimizer=optim.Adam(model.parameters())
"""
这是一个而计算二分类分布之间差别的 损失函数
"""
criterion=nn.BCEWithLogitsLoss()
model=model.to(device)
criterion=criterion.to(device)"""
计算预测的准确率
"""def  binary_accuacry(preds,y):"""returns accuacry per batch  ie if you get 8/10 right this returns  0.8 NOT 8"""# round predictions to the closest integer"""将输出值进行 sigmoid 到0-1之间 然后进行四舍五入"""rounded_preds=torch.round(torch.sigmoid(preds))correct=(rounded_preds==y).float()acc=correct.sum()/len(correct)return acc"""
开始训练模型
"""
def train(model,iterator,optimizer,criterion):epoch_loss=0epoch_acc=0model.train()for batch in iterator:optimizer.zero_grad()"""将平局之后的句子向量放到线性层 进行分类   [batch_Size,embed_Size]>>>[batch_Size,output_Size]output_size=1要对形状进行变化 """predictions=model(batch.text).squeeze(1)loss=criterion(predictions,batch.label)acc=binary_accuacry(predictions,batch.label)loss.backward()optimizer.step()epoch_loss+=loss.item()epoch_acc+=acc.item()return  epoch_loss/len(iterator),epoch_acc/len(iterator)"""
评估模型
"""
def evaluate(model,iterator,criterion):epoch_loss=0epoch_acc=0model.eval()with torch.no_grad():for batch in iterator:predictions=model(batch.text).suqeeze(1)loss=criterion(predictions,batch.label)acc=binary_accuacry(predictions,batch.label)epoch_loss+=loss.item()epoch_acc+=loss.item()return  epoch_loss/len(iterator),epoch_acc/len(iterator)import time def  epoch_time(start_time,end_time):elapsed_time=end_time-start_timeelapsed_mins=int(elapsed_time/60)elased_secs=int(elapsed_time-(elapsed_mins*60))return  elapsed_mins,elased_secsN_EPOCH=10
best_valid_loss=float('inf')for epoch in range(N_EPOCH):start_time=time.time()train_loss,train_acc=train(model,train_iteratorn,optimizer,criterion)valid_loss,valid_acc=evaluate(moedl,valid_iterator.criterion)end_time=time.time()epoch_mins,epoch_secs=epoch_time(start_time,end_time)if valid_loss<best_valid_loss:best_valid_loss=valid_losstorch.save(model.state_dict(),'wordavg-modle.pt')print(f'Epoch: {epoch+1:02} | Epoch Time: {epoch_mins}m {epoch_secs}s')print(f'\tTrain Loss: {train_loss:.3f} | Train Acc: {train_acc*100:.2f}%')print(f'\t Val. Loss: {valid_loss:.3f} |  Val. Acc: {valid_acc*100:.2f}%')"""
加载模型并且进行预测
"""
import spacynlp =spacy.load('en')def predict_sentiment(sentence):"""分词"""tokenized=[tok.text for  tok  in  nlp.tokenizer(sentence)]# 转化为数字indexed=[TEXT.vocab.stoi[t] for  t in tokenizedk]#  [seq_len]tensor=torch.LongTensor(indexed).to(device)# [seq_len  batch_Size]tensor=tensor.unsqueeze(1)prediction=torch.sigmoid(model(tensor))return  prediction.item()"""
预测例子
"""
predict_sentiment("this film is  terrible")

Word Averaging模型做文本分类 稳定效果好模型简单相关推荐

  1. bert模型可以做文本主题识别吗_GitHub - jkszw2014/TextClassify_with_BERT: 使用BERT模型做文本分类;面向工业用途...

    TextClassify_with_BERT 使用BERT模型做文本分类:面向工业用途 自己研究了当前开源的使用BERT做文本分类的许多存储库,各有各的缺点.通病就是面向学术,不考虑实际应用. 使用t ...

  2. 猿创征文丨深度学习基于双向LSTM模型完成文本分类任务

    大家好,我是猿童学,本期猿创征文的第三期,也是最后一期,给大家带来神经网络中的循环神经网络案例,基于双向LSTM模型完成文本分类任务,数据集来自kaggle,对电影评论进行文本分类. 电影评论可以蕴含 ...

  3. 深度学习基于双向 LSTM 模型完成文本分类任务

    大家好,本期给大家带来神经网络中的循环神经网络案例,基于双向LSTM模型完成文本分类任务,数据集来自kaggle,对电影评论进行文本分类. 电影评论可以蕴含丰富的情感:比如喜欢.讨厌.等等.情感分析( ...

  4. 【NLP】相当全面:各种深度学习模型在文本分类任务上的应用

    论文标题:Deep Learning Based Text Classification:A Comprehensive Review 论文链接:https://arxiv.org/pdf/2004. ...

  5. Tensorlfow2.0 二分类和多分类focal loss实现和在文本分类任务效果评估

    Tensorlfow2.0 二分类和多分类focal loss实现和在文本分类任务效果评估 前言 二分类 focal loss 多分类 focal loss 测试结果 二分类focal_loss结果 ...

  6. bert使用做文本分类_使用BERT进行深度学习的多类文本分类

    bert使用做文本分类 Most of the researchers submit their research papers to academic conference because its ...

  7. 使用bert模型做句子分类

    使用bert模型微调做下游任务,在goole发布的bert代码和huggingface的transformer项目中都有相应的任务,有的时候只需要把代码做简单的修改即可使用.发现代码很多,我尝试着自己 ...

  8. 贝叶斯分类器做文本分类案例

    贝叶斯分类器做文本分类 文本分类是现代机器学习应用中的一大模块,更是自然语言处理的基础之一.我们可以通过将文字数据处理成数字数据,然后使用贝叶斯来帮助我们判断一段话,或者一篇文章中的主题分类,感情倾向 ...

  9. transformer做文本分类的keras实现完整版

    背景 目前csdn上搜索到的keras的版本实现,排在前面的是: https://blog.csdn.net/xiaosongshine/article/details/86595847 但是,这个文 ...

最新文章

  1. 炸了!一口气问了我18个JVM问题!
  2. .pyc文件_python专题shutil高阶文件操作
  3. node爬取某app数据_某APP次日留存数据报告
  4. [转] CMake入门
  5. NPOI 删除指定的行
  6. 在VS中安装/使用 MVVMLight
  7. 用python做自动化测试仪器_使用python进行windows自动化测试(1)
  8. n皇后问题c语言报告,关于N皇后问题
  9. 贺利坚老师汇编课程74笔记:按下esc键改变显示颜色
  10. mysql 5.1 到 mysql 5.2的出现的索引BTREE问题 use near 'USING BTREE
  11. 群晖系统,部署JAVA-JAR包,SpringBoot项目,手工启动
  12. 传感器的原理及应用有哪些
  13. c语言数组回文数编写字符串,回文数C语言(示例代码)
  14. 电脑开启移动热点手机一直显示正在获取ip
  15. 《Understanding WiFi Signal Frequency Features for Position-Independent Gesture Sensing》论文总结
  16. 基于机器学习的视频防抖处理
  17. 摘录 | 《记一忘三二》
  18. db2建立表空间 linux,DB2实验教程:创建数据库/表空间
  19. 知云文献翻译打不开_还在为论文翻译烦恼吗?点进来帮您解决
  20. 用户选择好用的投票小程序最有用的投票小程序微信推送里投票制作教程

热门文章

  1. php 提取视频中的音频,如何把视频中的音频提取出来
  2. Three.js从入门到放弃
  3. python中的header_python中header是什么意思
  4. 修改gh-ost源码实现两表在线高速复制
  5. 2021ASC超算竞赛QuEST配置与实战(量子计算)
  6. 【字节跳动】 https://job.bytedance.com/campus 内推码:MZ9BJHD 电话:13855119574 邮箱:yinxiang.stephen@bytedance.com
  7. 输入两个正整数,求其最大公约数。
  8. 智联物联路由器openvpn客户端连接linux服务器通讯基本配置
  9. 推荐系统实战(5)——基于内容的推荐算法(CB)
  10. html 银联图标,银联标志logo图片 云闪付app扫银联标识领获红包