深度学习100例|第43天:文本卷积神经网络(textcnn)新闻文本分类实战(代码片段)

K同学啊 K同学啊     2022-11-29     434

关键词:


大家好,我是K同学啊!

今天给大家带来一个简单的中文新闻分类实例,采用的是TextCNN算法模型。TextCNN的主要流程是:获取文本的局部特征:通过不同的卷积核尺寸来提取文本的N-Gram信息(N-Gram是一种基于统计语言模型的算法),然后通过最大池化操作来突出各个卷积操作提取的最关键信息,拼接后通过全连接层对特征进行组合,采用的是交叉熵损失函数。

✨ 镜像项目:基于BERT模型的文本分类研究 TensorFlow2实现(内附源码)【自然语言处理NLP-100例】

本项目使用的是THUCNews数据集(缩减版),实现了财经房产股票教育科技社会时政体育游戏娱乐等10类文本的高效分类,最后的分类准确率达到了87.7%

数据示例:

🚀 我的环境:

  • 语言环境:Python3.6.5
  • 编译器:PyCharm
  • 深度学习环境:TensorFlow2.4.1
  • 本文代码&数据:公众号(K同学啊)内回复 DL+43可以获取数据

文章目录

一、设置GPU

#导入库包
import tensorflow.keras as keras
import numpy as np
import os
from config import Config
from sklearn import metrics
from keras.models import Sequential
from tensorflow.keras.models import Sequential
from tensorflow.keras.layers import Dense, Embedding,Dropout,Conv1D,ReLU,GlobalMaxPool1D,InputLayer

如果使用的是CPU可以注释掉下面的代码。

import tensorflow as tf
gpus = tf.config.list_physical_devices("GPU")

if gpus:
    gpu0 = gpus[0] #如果有多个GPU,仅使用第0个GPU
    tf.config.experimental.set_memory_growth(gpu0, True) #设置GPU显存用量按需使用
    tf.config.set_visible_devices([gpu0],"GPU")

二、预处理类

trainingSet_path = "cnews.train.txt"
valSet_path = "cnews.val.txt"
model_save_path = "CNN_model.h5"
testingSet_path = "cnews.test.txt"


#创建 文本处理类:preprocesser
class preprocesser(object):
    def __init__(self):
        self.config = Config()

    # 读取文本txt 函数
    def read_txt(self, txt_path):
        with open(txt_path, "r", encoding='utf-8') as f:
            data = f.readlines()
        labels = []
        contents = []
        for line in data:
            label, content = line.strip().split('\\t')
            labels.append(label)
            contents.append(content)
        return labels, contents
    # 读取分词文档
    def get_vocab_id(self):

        vocab_path = "cnews.vocab.txt"
        with open(vocab_path, "r", encoding="utf-8") as f:
            infile = f.readlines()
        vocabs = list([word.replace("\\n", "") for word in infile])
        vocabs_dict = dict(zip(vocabs, range(len(vocabs))))
        return vocabs, vocabs_dict

    # 获取新闻属性id 函数
    def get_category_id(self):
     
        categories = ["体育", "财经", "房产", "家居", "教育", "科技", "时尚", "时政", "游戏", "娱乐"]
        cates_dict = dict(zip(categories, range(len(categories))))
        return cates_dict

    #将语料中各文本转换成固定max_length后返回各文本的标签与文本tokens
    def word2idx(self, txt_path, max_length):

        # vocabs:分词词汇表
        # vocabs_dict:各分词的索引
        vocabs, vocabs_dict = self.get_vocab_id()
        # cates_dict:各分类的索引
        cates_dict = self.get_category_id()

        # 读取语料
        labels, contents = self.read_txt(txt_path)
        # labels_idx:用来存放语料中的分类
        labels_idx = []
        # contents_idx:用来存放语料中各样本的索引
        contents_idx = []

        # 遍历语料
        for idx in range(len(contents)):
            # tmp:存放当前语句index
            tmp = []
            # 将该idx(样本)的标签加入至labels_idx中
            labels_idx.append(cates_dict[labels[idx]])
            # contents[idx]:为该语料中的样本遍历项
            # 遍历contents中各词并将其转换为索引后加入contents_idx中
            for word in contents[idx]:
                if word in vocabs:
                    tmp.append(vocabs_dict[word])
                else:
                    # 第5000位设置为未知字符
                    tmp.append(5000)
            # 将该样本index后结果存入contents_idx作为结果等待传回
            contents_idx.append(tmp)

        # 将各样本长度pad至max_length
        x_pad = keras.preprocessing.sequence.pad_sequences(contents_idx, max_length)
        y_pad = keras.utils.to_categorical(labels_idx, num_classes=len(cates_dict))

        return x_pad, y_pad
    
    def word2idx_for_sample(self, sentence, max_length):
        # vocabs:分词词汇表
        # vocabs_dict:各分词的索引
        vocabs, vocabs_dict = self.get_vocab_id()
        result = []
        # 遍历语料
        for word in sentence:
            # tmp:存放当前语句index
                if word in vocabs:
                    result.append(vocabs_dict[word])
                else:
                    # 第5000位设置为未知字符,实际中为vocabs_dict[5000],使得vocabs_dict长度变成len(vocabs_dict+1)
                    result.append(5000)

        x_pad = keras.preprocessing.sequence.pad_sequences([result], max_length)
        return x_pad

pre = preprocesser() # 实例化preprocesser()类

三、参数设定

num_classes = 10     # 类别数
vocab_size = 5000    #语料词大小
seq_length = 600     #词长度

conv1_num_filters = 128   # 第一层输入卷积维数
conv1_kernel_size = 1     # 卷积核数

conv2_num_filters = 64   # 第二层输入卷维数
conv2_kernel_size = 1    # 卷积核数

hidden_dim = 128         # 隐藏层维度
dropout_keep_prob = 0.5  # dropout层丢弃0.5

batch_size = 64     # 每次训练批次数  

四、构建模型

def TextCNN():
    #创建模型序列
    model = Sequential()
    model.add(InputLayer((seq_length,)))
    model.add(Embedding(vocab_size+1, 256, input_length=seq_length))
    model.add(Conv1D(conv1_num_filters, conv1_kernel_size, padding="SAME"))
    model.add(Conv1D(conv2_num_filters, conv2_kernel_size, padding="SAME"))
    model.add(GlobalMaxPool1D())
    model.add(Dense(hidden_dim))
    model.add(Dropout(dropout_keep_prob))
    model.add(ReLU())
    model.add(Dense(num_classes, activation="softmax"))
    model.compile(loss="categorical_crossentropy",
                  optimizer="adam",
                  metrics=["acc"])

    return model

五、模型训练函数

def train(epochs):

    model = TextCNN()
    model.summary()

    x_train, y_train = pre.word2idx(trainingSet_path, max_length=seq_length)
    x_val, y_val = pre.word2idx(valSet_path, max_length=seq_length)

    model.fit(x_train, y_train,batch_size=batch_size,epochs=epochs,validation_data=(x_val, y_val))

    model.save(model_save_path, overwrite=True)

六、模型测试函数

def test():

    if os.path.exists(model_save_path):
        model = keras.models.load_model(model_save_path)
        print("-----model loaded-----")
        model.summary()

    x_test, y_test = pre.word2idx(testingSet_path, max_length=seq_length)
    print(x_test.shape)
    print(type(x_test))
    print(y_test.shape)
    pre_test = model.predict(x_test)
    print(metrics.classification_report(np.argmax(pre_test, axis=1), np.argmax(y_test, axis=1)))

七、模型训练与预测

if __name__ == '__main__':

    train(20)  # 训练模型
    
    model = keras.models.load_model(model_save_path)
    print("-----model loaded-----")
    model.summary()
    test = preprocesser()

    # 测试文本
    x_test = '5月6日,上海莘庄基地田径特许赛在第二体育运动学校鸣枪开赛。男子110米栏决赛,19岁崇明小囡秦伟搏以13.35秒的成绩夺冠,创造本赛季亚洲最佳。谢文骏迎来赛季首秀,以13.38秒获得亚军'
    x_test = test.word2idx_for_sample(x_test, 600)

    categories = ["体育", "财经", "房产", "家居", "教育", "科技", "时尚", "时政", "游戏", "娱乐"]

    pre_test = model.predict(x_test)

    index = int(np.argmax(pre_test, axis=1)[0])

    print('该新闻为:', categories[index])

训练输出:

Epoch 1/20
782/782 [==============================] - 6s 4ms/step - loss: 0.7376 - acc: 0.7666 - val_loss: 0.4742 - val_acc: 0.8552
Epoch 2/20
782/782 [==============================] - 3s 4ms/step - loss: 0.3939 - acc: 0.8814 - val_loss: 0.4187 - val_acc: 0.8702
......
Epoch 19/20
782/782 [==============================] - 3s 4ms/step - loss: 0.1658 - acc: 0.9455 - val_loss: 0.5052 - val_acc: 0.8692
Epoch 20/20
782/782 [==============================] - 3s 4ms/step - loss: 0.1647 - acc: 0.9454 - val_loss: 0.5027 - val_acc: 0.8768

该新闻为: 教育

开发者涨薪指南 48位大咖的思考法则、工作方式、逻辑体系

深度学习100例-卷积神经网络(cnn)猴痘病识别|第45天

本文为 查看详情

深度学习100例-卷积神经网络(cnn)猴痘病识别|第45天

本文为 查看详情

深度学习100例-卷积神经网络(inceptionv3)识别手语|第13天

查看详情

深度学习100例|第27天-卷积神经网络(cnn):艺术作品识别(代码片段)

我的知乎我的微信公众号我的CSDN下载本文源码+数据需要帮助Ctrl+D:收藏本页面大家好,我是K同学啊!今天的案例是世界名画的分类识别🚀我的环境:语言环境:Python3.6.5编译器:jupyternotebook深... 查看详情

记录|深度学习100例-卷积神经网络(cnn)服装图像分类|第3天(代码片段)

记录|深度学习100例-卷积神经网络(CNN)服装图像分类|第3天1.服装图像分类效果图原始训练图如下:测试图:预测标签及实际标签如下:可以看到正确预测训练损失/准确度图:2.源码#深度学习100例-卷积神... 查看详情

深度学习100例|第24天-卷积神经网络(xception):动物识别(代码片段)

...后来不是说填坑嘛,之前已经写一篇深度学习100例-卷积神经网络(LeNet-5)深度学习里的“HelloWord”|第22天来填补LeNet-5的坑。今天继续写一篇关于Xception模型的实例,实现了四种动物(狗、猫、鸡、马)的识别分类。希望大家多... 查看详情

记录|深度学习100例-卷积神经网络(cnn)minist数字分类|第1天(代码片段)

记录|深度学习100例-卷积神经网络(CNN)minist数字分类|第2天1.minist0-9数字分类效果图数据集如下:分类及预测图如下:预测标签值和真实标签值如下图所示,成功预测训练Loss/Accuracy图如下:源码#深度学习1... 查看详情

记录|深度学习100例-卷积神经网络(cnn)彩色图片分类|第2天(代码片段)

记录|深度学习100例-卷积神经网络(CNN)彩色图片分类|第2天1.彩色图片分类效果图数据集如下:测试图1如下训练/验证精确图如下:优化后:测试图——打印预测标签:优化后:测试图——打印预测标签和真... 查看详情

深度学习保姆级教程(附代码+数据)

...的实例教程,目前是入门阶段。【深度学习100例-卷积神经网络(CNN)实现mnist手写数字识别|第1天】【深度学习100例-卷积神经网络(CNN)彩色图片分类|第2天】【深度学习100例-卷积神经网络(CNN)服装... 查看详情

深度学习100例-卷积神经网络(inception-resnet-v2)识别交通标志|第14天

查看详情

深度学习100例-卷积神经网络(cnn)服装图像分类|第3天(代码片段)

文章目录一、前期工作1.设置GPU2.导入数据3.归一化4.调整图片格式5.可视化二、构建CNN网络三、编译四、训练模型五、预测六、模型评估一、前期工作我的环境:语言环境:Python3.6.5编译器:jupyternotebook深度学习环境:TensorFlow2来... 查看详情

深度学习100例-卷积神经网络(cnn)实现车牌识别|第15天

文章目录一、前期工作1.设置GPU2.导入数据3.数据可视化4.标签数字化二、构建一个tf.data.Dataset1.预处理函数2.加载数据3.配置数据三、搭建网络模型四、设置动态学习率五、编译六、训练七、模型评估八、保存和加载模型九、预测... 查看详情

深度学习100例-卷积神经网络(cnn)花朵识别|第4天(代码片段)

文章目录一、前期工作1.设置GPU2.下载数据3.检查数据二、数据预处理1.加载数据2.可视化数据3.再次检查数据4.配置数据集三、构建CNN网络四、编译五、训练模型六、模型评估一、前期工作本文将采用CNN实现花朵识别我的环境:语... 查看详情

深度学习100例-卷积神经网络(cnn)实现mnist手写数字识别|第1天

...模型五、预测六、知识点详解1.MNIST手写数字数据集介绍2.神经网络程序说明3.网络结构说明我的环境:语言环境:Python3.6.5编译器:jupyternotebook深度学习环境:TensorFlow2来自专栏:【深度学习100例 查看详情

深度学习100例|第41天-卷积神经网络(cnn):urbansound8k音频分类(语音识别)

查看详情

深度学习100例-卷积神经网络(lenet-5)深度学习里的“helloword”|第22天(代码片段)

大家好,我是「K同学啊」!前几天翻译了一篇讲十大CNN结构的文章(「多图」图解10大CNN架构),原作者思路十分清晰,从时间线上,将近年来CNN发展过程中一些比较重要的网络模型做了一一介绍。我... 查看详情

深度学习100例-卷积神经网络(lenet-5)深度学习里的“helloword”|第22天(代码片段)

大家好,我是「K同学啊」!前几天翻译了一篇讲十大CNN结构的文章(「多图」图解10大CNN架构),原作者思路十分清晰,从时间线上,将近年来CNN发展过程中一些比较重要的网络模型做了一一介绍。我... 查看详情

深度学习100例-卷积神经网络(cnn)识别神奇宝贝小智一伙|第16天

文章目录一、前期工作1.设置GPU2.导入数据3.查看数据二、数据预处理1.加载数据2.可视化数据3.再次检查数据4.配置数据集三、调用官方网络模型四、设置动态学习率五、编译六、训练模型七、模型评估八、保存and加载模型九、预... 查看详情