NLP实战:使用Word2vec实现文本分类

这篇具有很好参考价值的文章主要介绍了NLP实战:使用Word2vec实现文本分类。希望对大家有所帮助。如果存在错误或未考虑完全的地方,请大家不吝赐教,您也可以点击"举报违法"按钮提交疑问。

目录

一、数据预处理

1、加载数据

2. 构建词典

3.生成数据批次和迭代器

二、模型构建

1.搭建模型

2.初始化模型

3.定义训练与评估函数

三、训练模型

1. 拆分数据集并运行模型

2. 测试指定数据


🍨 本文为[🔗365天深度学习训练营]内部限免文章(版权归 *K同学啊* 所有)
🍖 作者:[K同学啊]

一、数据预处理
1. 任务说明
本次将加入Word2vec使用PyTorch实现中文文本分类,Word2Vec 则是其中的一种词嵌入方法,是一种用于生成词向量的浅层神经网络模型,由Tomas Mikolov及其团队于2013年提出。Word2Vec通过学习大量文本数据,将每个单词表示为一个连续的向量,这些向量可以捕捉单词之间的语义和句法关系。更详细的内容可见训练营内的NLP基础知识,数据示例如下:

NLP实战:使用Word2vec实现文本分类

📌 本周任务:
●结合Word2Vec文本内容(第1列)预测文本标签(第2列)
●尝试根据第2周的内容独立实现,尽可能的不看本文的代码
●进一步了解并学习Word2Vec

一、数据预处理

1、加载数据

import torch
import torch.nn as nn
import torchvision
from torchvision import transforms, datasets
import os,PIL,pathlib,warnings

warnings.filterwarnings("ignore")             #忽略警告信息

device = torch.device("cuda" if torch.cuda.is_available() else "cpu")
print(device)

cuda

import pandas as pd

# 加载自定义中文数据
train_data = pd.read_csv('./train.csv', sep='\t', header=None)
print(train_data)

NLP实战:使用Word2vec实现文本分类

# 构造数据集迭代器
def coustom_data_iter(texts, labels):
    for x, y in zip(texts, labels):
        yield x, y
        
x = train_data[0].values[:]
#多类标签的one-hot展开
y = train_data[1].values[:]

2. 构建词典

调用gensim库

from gensim.models.word2vec import Word2Vec
import numpy as np

# 训练 Word2Vec 浅层神经网络模型
w2v = Word2Vec(vector_size=100, #是指特征向量的维度,默认为100。
               min_count=3)     #可以对字典做截断. 词频少于min_count次数的单词会被丢弃掉, 默认值为5。

w2v.build_vocab(x)
w2v.train(x,                         
          total_examples=w2v.corpus_count, 
          epochs=20)

Word2Vec可以直接训练模型,一步到位。这里分了三步

  • 第一步构建一个空模型
  • 第二步使用 build_vocab 方法根据输入的文本数据 x 构建词典。build_vocab 方法会统计输入文本中每个词汇出现的次数,并按照词频从高到低的顺序将词汇加入词典中。
  • 第三步使用 train 方法对模型进行训练,total_examples 参数指定了训练时使用的文本数量,这里使用的是 w2v.corpus_count 属性,表示输入文本的数量
# 将文本转化为向量
def average_vec(text):
    vec = np.zeros(100).reshape((1, 100))
    for word in text:
        try:
            vec += w2v.wv[word].reshape((1, 100))
        except KeyError:
            continue
    return vec

# 将词向量保存为 Ndarray
x_vec = np.concatenate([average_vec(z) for z in x])

# 保存 Word2Vec 模型及词向量
w2v.save('w2v_model.pkl')

这段代码定义了一个函数 average_vec(text),它接受一个包含多个词的列表 text 作为输入,并返回这些词对应词向量的平均值。该函数

  • 首先初始化一个形状为 (1, 100) 的全零 numpy 数组来表示平均向量
  • 然后遍历 text 中的每个词,并尝试从 Word2Vec 模型 w2v 中使用 wv 属性获取其对应的词向量。如果在模型中找到了该词,函数将其向量加到 vec 中。如果未找到该词,函数会继续迭代下一个词
  • 最后,函数返回平均向量 vec

然后使用列表推导式将 average_vec() 函数应用于列表 x 中的每个元素。得到的平均向量列表使用 np.concatenate() 连接成一个 numpy 数组 x_vec,该数组表示 x 中所有元素的平均向量。x_vec 的形状为 (n, 100),其中 n 是 x 中元素的数量。

train_iter = coustom_data_iter(x_vec, y)
print(len(x),len(x_vec))

12100 12100

label_name = list(set(train_data[1].values[:]))
print(label_name)

['Radio-Listen', 'FilmTele-Play', 'Weather-Query', 'Music-Play', 'Audio-Play', 'Other', 'Travel-Query', 'Alarm-Update', 'HomeAppliance-Control', 'Calendar-Query', 'Video-Play', 'TVProgram-Play']

3.生成数据批次和迭代器

text_pipeline  = lambda x: average_vec(x)
label_pipeline = lambda x: label_name.index(x)
print(text_pipeline("你在干嘛"))

NLP实战:使用Word2vec实现文本分类

print(label_pipeline("Travel-Query"))

8

from torch.utils.data import DataLoader

def 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)

二、模型构建

1.搭建模型

from torch import nn

class 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)

2.初始化模型

num_class  = len(label_name)
vocab_size = 100000
em_size    = 12
model      = TextClassificationModel(num_class).to(device)

3.定义训练与评估函数

import time

def train(dataloader):
    model.train()  # 切换为训练模式
    total_acc, train_loss, total_count = 0, 0, 0
    log_interval = 50
    start_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与loss
        total_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_time
            print('| 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, 0
            start_time = time.time()

def evaluate(dataloader):
    model.eval()  # 切换为测试模式
    total_acc, train_loss, total_count = 0, 0, 0

    with 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

torch.nn.utils.clip_grad_norm_(model.parameters(), 0.1)是一个PyTorch函数,用于在训练神经网络时限制梯度的大小。这种操作被称为梯度裁剪(gradient clipping),可以防止梯度爆炸问题,从而提高神经网络的稳定性和性能。

在这个函数中:

  • model.parameters()表示模型的所有参数。对于一个神经网络,参数通常包括权重和偏置项。
  • 0.1是一个指定的阈值,表示梯度的最大范数(L2范数)。如果计算出的梯度范数超过这个阈值,梯度会被缩放,使其范数等于阈值。

梯度裁剪的主要目的是防止梯度爆炸。梯度爆炸通常发生在训练深度神经网络时,尤其是在处理长序列数据的循环神经网络(RNN)中。当梯度爆炸时,参数更新可能会变得非常大,导致模型无法收敛或出现数值不稳定。通过限制梯度的大小,梯度裁剪有助于解决这些问题,使模型训练变得更加稳定。

三、训练模型

1. 拆分数据集并运行模型

from torch.utils.data.dataset  import random_split
from torchtext.data.functional import to_map_style_dataset
# 超参数
EPOCHS     = 10 # epoch
LR         = 5  # 学习率
BATCH_SIZE = 64 # batch size for training

criterion = 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_acc
    print('-' * 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)

NLP实战:使用Word2vec实现文本分类

test_acc, test_loss = evaluate(valid_dataloader)
print('模型准确率为:{:5.4f}'.format(test_acc))

 模型准确率为:0.8814

2. 测试指定数据

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("cpu")

print("该文本的类别是:%s" %label_name[predict(ex_text_str, text_pipeline)])

NLP实战:使用Word2vec实现文本分类文章来源地址https://www.toymoban.com/news/detail-495049.html

到了这里,关于NLP实战:使用Word2vec实现文本分类的文章就介绍完了。如果您还想了解更多内容,请在右上角搜索TOY模板网以前的文章或继续浏览下面的相关文章,希望大家以后多多支持TOY模板网!

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

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

相关文章

  • 【NLP】Word2vec概念和演进史

            “万物都有一种模式,它是我们宇宙的一部分。它具有对称、优雅和优雅——这些品质你总能在真正的艺术家捕捉到的作品中找到。” ~ 沙丘 (1965)         对于word2vec,它不是一个或一种算法,而是一系列思想和算法的综合。本文通过有限篇幅,试图穿越思想跨

    2024年02月11日
    浏览(43)
  • 【NLP】如何实现快速加载gensim word2vec的预训练的词向量模型

    通过以下代码,实现加载word2vec词向量,每次加载都是几分钟,效率特别低。 (1)方案一 第一次加载后保存为能够快速加载的文件,第二次加载就能快读读取。 (2)方案二 第一次加载后,只将使用到的词向量以表格的形式保存到本地,第二次读取就不需要加载全部word2ve

    2024年03月14日
    浏览(46)
  • NLP——分布式语义 Distributional Semantics:Word Vectors;Word2Vec

    传统的词汇数据库(Lexical Database),如WordNet,是自然语言处理中一种常见的资源,用于提供词汇的定义、词义关系(如同义词、反义词)和词汇层次结构(如上下位词)。虽然这些资源在许多任务中都非常有用,但它们也存在一些限制,这促使了分布式语义的发展。以下是

    2024年02月08日
    浏览(48)
  • Word2Vec模型——将文本转换成向量的方法

            在美赛的时候,用了一下这个模型,发一下。         Word2Vec是一种用于将文本转换为向量表示的技术。它是Google在2013年开发的一种工具,主要用于将单词转换为向量表示,并在向量空间中找到单词之间的语义关系。Word2Vec模型有两种架构:连续词袋模型(Conti

    2023年04月21日
    浏览(34)
  • NLP入门:word2vec & self-attention & transformer & diffusion的技术演变

    这一段时间大模型的相关进展如火如荼,吸引了很多人的目光;本文从nlp领域入门的角度来总结相关的技术路线演变路线。 1、introduction 自然语言处理(Natural Language Processing),简称NLP,是通过统计学、数学模型、机器学习等相关技术研究人类语言的特征,对其进行数学的表

    2024年02月11日
    浏览(55)
  • 【自然语言】使用词袋模型,TF-IDF模型和Word2Vec模型进行文本向量化

    一、任务目标 python代码写将 HarryPorter 电子书作为语料库,分别使用词袋模型,TF-IDF模型和Word2Vec模型进行文本向量化。 1. 首先将数据预处理,Word2Vec 训练时要求考虑每个单词前后的五个词汇,地址为 作为其上下文 ,生成的向量维度为50维 2.分别搜索 courtroom 和 wizard 这两个词

    2024年04月14日
    浏览(47)
  • NLP自然语言处理理论解释(单词分布式表示,共现矩阵,word2vec,CBOW模型详解)

    自然语言处理:一种能让计算机理解人类语言的技术,换而言之自然语言处理的目标就是让计算机理解人说的话, 单词的含义 让计算机理解语言,首先要理解我们的单词,有三种方法,1.基于同义词词典,2.基于计数方法,3.基于推理的方法(word2vec)。 单词分布式表示 大家都

    2024年02月03日
    浏览(49)
  • 基于Word2vec词聚类的关键词实现

    基于Word2Vec的词聚类提取包括以下步骤: 整个流程的核心在于使用Word2Vec模型得到词向量,然后通过聚类算法将相似的词语归为一簇,最终提取每个簇的代表性词语作为。这种方法能够捕捉词语之间的语义关系,提高的表达力。 词向量的预处理 基于word2

    2024年01月18日
    浏览(54)
  • Word2Vec详解

    Word2Vec 基本思想:通过训练将每一个词映射成一个固定长度的向量,所有向量构成一个词向量空间,每一个向量(单词)可以看作是向量空间中的一个点,意思越相近的单词距离越近。 如何把词转换为向量? 通常情况下,我们可以维护一个查询表。表中每一行都存储了一个特

    2024年02月13日
    浏览(44)
  • 论文精读--word2vec

    word2vec从大量文本语料中以无监督方式学习语义知识,是用来生成词向量的工具 把文本分散嵌入到另一个离散空间,称作分布式表示,又称为词嵌入(word embedding)或词向量 We propose two novel model architectures for computing continuous vector representations of words from very large data sets. The qua

    2024年02月22日
    浏览(48)

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

支付宝扫一扫打赏

博客赞助

微信扫一扫打赏

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

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

二维码1

领取红包

二维码2

领红包