今天自己尝试使用LSTM对电影评论进行简单的情感分析

代码中npy文件:

代码使用的数据集是IMDB,网盘地址:

首先读取已经做好的词向量模型

import numpy as np

# 这里有两个表,一个是ID和单词的映射关系,一个是ID和词向量的映射关系

wordsList = np.load('./npy/wordsList.npy')

wordsList = wordsList.tolist()

wordsList = [word.decode('UTF-8') for word in wordsList]

wordVectors = np.load('./npy/wordVectors.npy')

这里可以打印看看维数和长度等

# 打印长度

print(len(wordsList))

print(wordVectors.shape)

400000

(400000, 50)

这里先举个简单的例子:

我们是先找到单词的索引index,然后再通过Index找到对应词的词向量(50维)

nameIndex = wordsList.index('name')

wordVectors[nameIndex]

array([ 0.20957 , 0.75197 , -0.48559 , 0.1302 , 0.60071 , 0.43273 ,

-0.95424 , -0.19335 , -0.66756 , -0.25893 , 0.66367 , 1.0509 ,

0.10627 , -0.75438 , 0.45617 , 0.37878 , -0.40237 , 0.1821 ,

-0.028768, 0.24349 , -0.35723 , -0.55817 , 0.14103 , 0.58807 ,

0.076804, -1.972 , -1.4459 , 0.081884, -0.29207 , -0.65623 ,

2.718 , -0.96886 , -0.33354 , -0.19526 , 0.33918 , -0.24307 ,

0.29058 , -0.37178 , -0.38133 , -0.20901 , 0.48504 , 0.20702 ,

-0.5754 , -0.32403 , -0.19267 , -0.043298, -0.57702 , -0.4727 ,

0.42171 , -0.14112 ], dtype=float32)

所以通过这个操作我们可以得到每个词的向量表示,因此,句子就是在上面再增加一个维度,比如一个句子长度是20,那么等会变成词向量的表示就是(20,50)。当然这里只是举一个小例子,实际训练还需要设定一个固定的句子长度(多截少补),还需要考虑batch_size。

这里先读取训练数据集(积极和消极各25000条)

from os import listdir

from os.path import isfile, join

# 指定好数据集位置,这里需要一个个读取

positiveFiles = ['lmdb/train/pos/' + f for f in listdir('lmdb/train/pos/') if isfile(join('lmdb/train/pos/', f))]

negativeFiles = ['lmdb/train/neg/' + f for f in listdir('lmdb/train/neg/') if isfile(join('lmdb/train/neg/', f))]

numWords = []

# 分别统计积极和消极情感数据集

for pf in positiveFiles:

with open(pf, "r", encoding='utf-8') as f:

line = f.readline()

counter = len(line.split())

numWords.append(counter)

# print('积极情感数据集加载完毕')

for pf in negativeFiles:

with open(pf, "r", encoding='utf-8') as f:

line = f.readline()

counter = len(line.split())

numWords.append(counter)

# print('消极情感数据集加载完毕')

numFiles = len(numWords)

print('全部序列数量', numFiles)

print('全部词语数量', sum(numWords))

print('平均每个评论序列词语数量', sum(numWords)/len(numWords))

全部序列数量 25000

全部词语数量 5844680

平均每个评论序列词语数量 233.7872

我们需要确定最长序列长度,所以这里用图表形式先展示一下:

import matplotlib.pyplot as plt

%matplotlib inline

plt.hist(numWords, 50)

plt.xlabel('Sequence Length')

plt.ylabel('Frequency')

plt.axis([0, 1200, 0, 8000])

plt.show()

统计

从直方图可以粗略看到,序列长度在200左右占大部分。这里可以将最大长度设为250。

maxSeqLength = 250

然后需要将文本序列转换成索引矩阵,先用正则做一个简单的转换

import re

strip_special_chars = re.compile("[^A-Za-z0-9 ]+")

# 过滤一下

def cleanSentences(string):

string = string.lower().replace("
", " ")

return re.sub(strip_special_chars, "", string.lower())

接下来是对25000条序列都做一次 词->ID的映射 形成一个25000×250的矩阵,计算较久。直接使用处理好的索引矩阵文件,词->ID映射代码如下:

# ids = np.zeros((numFiles, maxSeqLength), dtype='int32')

# fileCounter = 0

# for pf in positiveFiles:

# with open(pf, "r") as f:

# indexCounter = 0

# line = f.readline()

# cleanedLine = cleanSentences(line)

# split = cleanedLine.split()

# for word in split:

# try:

# ids[fileCounter][indexCounter] = wordsList.index(word)

# except ValueError:

# ids[fileCounter][indexCounter] = 599999

# indexCounter = indexCounter + 1

# if indexCounter >= maxSeqLength:

# break

# fileCounter = fileCounter + 1

# for nf in negativeFiles:

# with open(nf, "r") as f:

# indexCounter = 0

# line = f.readline()

# cleanedLine = cleanSentences(line)

# split = cleanedLine.split()

# for word in split:

# try:

# ids[fileCounter][indexCounter] = wordsList.index(word)

# except ValueError:

# ids[fileCounter][indexCounter] = 599999

# indexCounter = indexCounter + 1

# if indexCounter >= maxSeqLength:

# break

# fileCounter = fileCounter + 1

# np.save('idsMatrix', ids)

ids = np.load('npy/idsMatrix.npy')

下面开始构建模型,使用tensorflow图模型。首先定义一些超参数,例如批处理大小,LSTM单元个数,分类类别和训练次数

batchSize = 24

lstmUnits = 64

numClasses = 2

numDimensions = 50

iterations = 50000

输入数据的维度应该是 batchSize×250(最大序列长度)×50(词向量维度)

输出数据的维度应该是 batchSize×2(分类数目)

import tensorflow as tf

tf.reset_default_graph()

labels = tf.placeholder(tf.float32, [batchSize, numClasses])

input_data = tf.placeholder(tf.int32, [batchSize, maxSeqLength]) # 这里只是中间结果,还没转换成词向量

data = tf.Variable(tf.zeros([batchSize, maxSeqLength, numDimensions]), dtype=tf.float32)

data = tf.nn.embedding_lookup(wordVectors, input_data)

这里可以打印看看data格式

print(data)

然后构造模型:先使用tf.nn.rnn_cell.BasicLSTMCell函数,然后设置一个dropout参数避免过拟合,最后输入到tf.nn.dynamic_rnn展开整个网络

lstmCell = tf.contrib.rnn.BasicLSTMCell(lstmUnits)

lstmCell = tf.contrib.rnn.DropoutWrapper(cell=lstmCell, output_keep_prob=0.75)

value, _ = tf.nn.dynamic_rnn(lstmCell, data, dtype=tf.float32)

# 打印看看获取的数据

print(value)

# 权重参数初始化

weight = tf.Variable(tf.truncated_normal([lstmUnits, numClasses]))

bias = tf.Variable(tf.constant(0.1, shape=[numClasses]))

value = tf.transpose(value, [1, 0, 2])

# 取最终的结果值

last = tf.gather(value, int(value.get_shape()[0])-1)

prediction = (tf.matmul(last, weight) + bias)

print(prediction)

然后定义正确的预测函数和正确率评估参数。正确的预测形式是查看最后输出的0-1向量是否和标记的0-1向量相同

correctPred = tf.equal(tf.argmax(prediction, 1), tf.argmax(labels, 1))

accuracy = tf.reduce_mean(tf.cast(correctPred, tf.float32))

最后,使用一个交叉熵损失函数作为损失值。对于优化器,使用Adam,并且采用默认的学习率:

loss = tf.reduce_mean(tf.nn.softmax_cross_entropy_with_logits(logits=prediction, labels=labels))

optimizer = tf.train.AdamOptimizer().minimize(loss)

为了训练,需要定义辅助函数:

from random import randint

# 制作batch数据,通过数据集索引位置来设置训练集和测试集

# 并且让batch中正负样本各占一半,同时给定其当前标签

def getTrainBatch():

labels = []

arr = np.zeros([batchSize, maxSeqLength])

for i in range(batchSize):

if (i % 2 == 0):

num = randint(1, 11499)

labels.append([1,0])

else:

num = randint(13499, 24999)

labels.append([0,1])

arr[i] = ids[num-1:num]

return arr, labels

def getTestBatch():

labels = []

arr = np.zeros([batchSize, maxSeqLength])

for i in range(batchSize):

num = randint(11499, 13499)

if (num <= 12499):

labels.append([1,0])

else:

labels.append([0,1])

arr[i] = ids[num-1:num]

return arr, labels

训练

sess = tf.InteractiveSession()

saver = tf.train.Saver()

sess.run(tf.global_variables_initializer())

for i in range(iterations):

# 通过辅助函数拿到batch数据

nextBatch, nextBatchLabels = getTrainBatch()

sess.run(optimizer, {input_data: nextBatch, labels: nextBatchLabels})

# 每隔1000次打印一下当前的结果

if (i % 100 == 0 and i != 0):

loss_ = sess.run(loss, {input_data: nextBatch, labels: nextBatchLabels})

accuracy_ = sess.run(accuracy, {input_data: nextBatch, labels: nextBatchLabels})

print("iteration {}/{}...".format(i+1, iterations),

"loss {}...".format(loss_),

"accuracy {}...".format(accuracy_))

# 每1W次保存一下当前模型

if (i % 10000 == 0 and i != 0):

save_path = saver.save(sess, "models/pretrained_lstm.ckpt", global_step=i)

print("saved to %s" % save_path)

训练大概就是这样,因为我的笔记本太差,跑太久了。所以设置每100次打印一次。有条件的可以跑一下。

下面是在测试集上面跑的代码:

sess = tf.InteractiveSession()

saver = tf.train.Saver()

saver.restore(sess, tf.train.latest_checkpoint('models'))

然后导入测试数据集,进行测试

test_iterations = 10

for i in range(test_iterations):

nextBatch, nextBatchLabels = getTestBatch()

print("Accuracy for this batch:", (sess.run(accuracy, {input_data: nextBatch, labels: nextBatchLabels})) * 100)

lstm训练情感分析的优点_LSTM对电影评论进行简单的情感分析相关推荐

  1. python电影评论情感分析_NLP文本分类问题-电影评论的情感分析

    从头开始学习嵌入 import pandas as pd import numpy as np #读取csv文件 train = pd.read_csv('/kaggle/input/imdb-dat ...

  2. python爬取京东评论分析_Python爬取京东商品评论+制作关键字云+情感分析图

    首先我们要了解一下,我们用requests包爬取的都只是写在HTML页面上的数据,但是呢,现在很多网站的数据都是通过js代码生成的,除非你找到它,不然是爬取不到的. 首先我随意打开一个京东的商品的详情 ...

  3. linux input输入子系统分析《二》:s3c2440的ADC简单驱动实例分析

    1      mini2440的ADC驱动实例 这节与输入子系统无关,出现在这里是因为后面的章节会讲到触摸屏输入子系统驱动,由于触摸屏也使用ADC,因此本节是为了说明ADC通过驱动代码是如何控制的. ...

  4. 新手体验 kaggle上的电影评论情感分析

    数据集查看 ## 任务描述: "可爱的老式和愚蠢的人之间有一条细线,而基督山伯爵--从未在两边安定下来." Rotten Tomatoes电影评论数据集是用于情感分析的电影评论语料 ...

  5. 【自然语言处理(NLP)】基于FNN网络的电影评论情感分析

    [自然语言处理(NLP)]基于FNN网络的电影评论情感分析 作者简介:在校大学生一枚,华为云享专家,阿里云专家博主,腾云先锋(TDP)成员,云曦智划项目总负责人,全国高等学校计算机教学与产业实践资源建 ...

  6. 【自然语言处理】基于NLP的电影评论情感分析模型比较

    基于NLP的电影评论情感分析模型比较 一段时间以来,使用机器学习的 NLP 任务借助 BERT(Bidirectional Encoder Representations from Transform ...

  7. 情感分析之电影评论分析-基于Tensorflow的LSTM

    1. 深度学习在自然语言处理中的应用 自然语言处理是教会机器如何去处理或者读懂人类语言的系统,目前比较热门的方向,包括如下几类: 对话系统 - 比较著名的案例有:Siri,Alexa 和 Cortan ...

  8. 基于LSTM的情感识别在鹅漫电商评论分析中的实践与应用

    导语 深度学习(深度神经网络)作为机器学习的一个重要分支,持续推动了很多领域的研究和应用取得新的进展,其中包括文本处理领域的情感分类问题.由于可以对文本进行更有效的编码及表达,基于深度学习的情感分类对 ...

  9. 自然语言处理-应用场景-文本分类:基于LSTM模型的情感分析【IMDB电影评论数据集】--(重点技术:自定义分词、文本序列化、输入数据批次化、词向量迁移使用)

    文本情感分类 1. 案例介绍 现在我们有一个经典的数据集IMDB数据集,地址:http://ai.stanford.edu/~amaas/data/sentiment/,这是一份包含了5万条流行电影的 ...

最新文章

  1. 学生卡变成普通卡_刚接触流量卡的小白看这一篇就够了!!!
  2. LambdaMART简介——基于Ranklib源码(一 lambda计算)
  3. 报告显示H.264份额进一步提升 1080p最受欢迎
  4. swift语言 编写 ios开发 第一个程序hello world!
  5. CSS样式小项目实战 - 网页变色小按钮
  6. freemarker 解析对象的某元素_Freemarker常用技巧(三)
  7. 用CLSID_FilterGraph+TV卡实现视频采集
  8. qq分享至空间、好友自定义分享样式
  9. 3月18日短线黑马牛股公开验证
  10. win10系统服务器错误,怎么处理Win10系统下提示内部服务器错误的情况
  11. 听歌识曲算法技术[语音识别]
  12. kali 上下载GitHub文件失败
  13. Win10系统自带功能,提高办公效率
  14. 测试用例的设计方法(全)
  15. 远程医疗是指通过计算机技术,E诊断:什么是远程医疗?
  16. 2015年高考物理复习重点
  17. 自习室风口!使用网上预约系统助力自习室预约
  18. 锐龙r9 6900hx和锐龙r7 6800h差距 r96900hx和r76800h选哪个好
  19. 4-8 验证“哥德巴赫猜想”
  20. app inventor我的漫画书

热门文章

  1. Redis 远程字典服务及shell全部命令汇总【点击可查看高清原图】(附 xmind思维导图原文件 百度网盘)
  2. mpvue 微信小程序_使用Vue.js开发微信小程序:开源框架mpvue解析
  3. 呕心沥血为小白总结13个学习网站-错过了你注定绕弯!
  4. Spring-AOP动态代理技术(底层代码)
  5. 力扣刷题常用数据结构和方法(java版本)
  6. Ehab Is an Odd Person
  7. TRDD got lost again
  8. 【jetson nano】两台ubuntu ssh远程连接控制
  9. redis安装,主从集群
  10. jQuery表单校验jquery.validate.js的使用