Appearance
情感分析及数据集
一、什么是情感分析
情感分析就是研究文本里 “隐藏” 的情绪,比如我们看电影评论、产品评价的时候,想知道这个评论是好评还是差评,这就是情感分析要解决的问题。它属于文本分类任务,把可变长度的文本序列(比如一段评论)转换成固定的类别,比如 “积极” 或者 “消极”。
情感分析的应用场景很多:
政治领域:分析公众对政策的情绪,了解大家对政策的支持度
金融领域:分析市场情绪,判断股票市场的走势
营销领域:分析用户对产品的评价,做产品研究和品牌管理
二、IMDb 电影评论数据集
我们用的是斯坦福大学的大型电影评论数据集(IMDb),这个数据集是从 IMDb 网站下载的电影评论,分成训练集和测试集,各有 25000 条评论,其中 “积极” 和 “消极” 的评论各占一半,刚好可以用来做二分类的情感分析任务。
三、读取数据集
首先我们需要下载并读取这个数据集,用 Python 代码实现:
python
import os
import d2l
# 下载并解压数据集
d2l.DATA_HUB['aclImdb'] = (
'http://ai.stanford.edu/~amaas/data/sentiment/aclImdb_v1.tar.gz',
'01ada507287d82875905620988597833ad4e0903'
)
data_dir = d2l.download_extract('aclImdb', 'aclImdb')
# 读取数据集的函数
def read_imdb(data_dir, is_train):
"""读取IMDb评论数据集的文本和标签"""
data, labels = [], []
# 遍历积极和消极标签的文件夹
for label in ('pos', 'neg'):
folder_name = os.path.join(data_dir, 'train' if is_train else 'test', label)
# 读取每个评论文件
for file in os.listdir(folder_name):
with open(os.path.join(folder_name, file), 'rb') as f:
# 读取评论文本,去掉换行符
review = f.read().decode('utf-8').replace('\n', '')
data.append(review)
# 给标签:积极是1,消极是0
labels.append(1 if label == 'pos' else 0)
return data, labels
# 读取训练集和测试集
train_data = read_imdb(data_dir, is_train=True)
test_data = read_imdb(data_dir, is_train=False)
# 查看训练集的数量和样例
print('训练集数目:', len(train_data[0]))
for x, y in zip(train_data[0][:3], train_data[1][:3]):
print('标签:', y, '评论内容:', x[:60])运行结果会显示:
Plain
训练集数目: 25000
标签: 1 评论内容: Zentropa has much in common with The Third Man, another noir
标签: 1 评论内容: Zentropa is the most original movie I've seen in years. If y
标签: 1 评论内容: Lars Von Trier is never backward in trying out new technique四、预处理数据集
计算机没法直接处理文本,我们需要把文本转换成数字,这一步就是预处理:
1. 词元化
把每个评论拆成一个个单词,也就是 “词元化”:
python
# 把评论拆成单词
train_tokens = d2l.tokenize(train_data[0], token='word')2. 创建词表
把所有出现的单词做成一个 “字典”,给每个单词一个编号,同时过滤掉出现次数少于 5 次的稀有单词,避免这些单词影响模型训练:
python
# 创建词表,过滤出现次数少于5次的单词
vocab = d2l.Vocab(train_tokens, min_freq=5, reserved_tokens=['<pad>'])3. 处理评论长度
每个评论的长度不一样,有的短有的长,我们用直方图看看评论的长度分布:
python
d2l.set_figsize()
d2l.plt.xlabel('每条评论的词元数量')
d2l.plt.ylabel('评论数量')
d2l.plt.hist([len(line) for line in train_tokens], bins=range(0, 1000, 50))
d2l.plt.show()从直方图可以看到,大部分评论的词元数量在 500 以内,所以我们把每个评论都截断或填充到 500 长度,这样每个评论的长度就一样了,方便后续训练:
python
import numpy as np
# 把每个评论截断或填充到500长度
train_features = np.array([d2l.truncate_pad(vocab[line], 500, vocab['<pad>']) for line in train_tokens])
test_features = np.array([d2l.truncate_pad(vocab[line], 500, vocab['<pad>']) for line in test_tokens])五、创建数据迭代器
最后我们把预处理好的数据转换成小批量的迭代器,这样训练模型的时候可以一次处理一批数据,提高效率:
python
def load_data_imdb(batch_size, num_steps=500):
"""返回IMDb数据集的训练、测试迭代器和词表"""
data_dir = d2l.download_extract('aclImdb', 'aclImdb')
train_data = read_imdb(data_dir, True)
test_data = read_imdb(data_dir, False)
# 词元化
train_tokens = d2l.tokenize(train_data[0], token='word')
test_tokens = d2l.tokenize(test_data[0], token='word')
# 创建词表
vocab = d2l.Vocab(train_tokens, min_freq=5)
# 处理评论长度
train_features = np.array([d2l.truncate_pad(vocab[line], num_steps, vocab['<pad>']) for line in train_tokens])
test_features = np.array([d2l.truncate_pad(vocab[line], num_steps, vocab['<pad>']) for line in test_tokens])
# 创建数据迭代器
train_iter = d2l.load_array((train_features, train_data[1]), batch_size)
test_iter = d2l.load_array((test_features, test_data[1]), batch_size, is_train=False)
return train_iter, test_iter, vocab
# 测试函数
train_iter, test_iter, vocab = load_data_imdb(batch_size=32)
print('词表大小:', len(vocab))
print('训练迭代器的一个批次形状:', next(iter(train_iter))[0].shape)运行结果会显示词表大小(大概 4 万多),还有训练批次的形状是(32, 500),也就是每个批次 32 条评论,每条评论 500 个词元。
六、小结
情感分析是文本分类任务,把文本转换成积极 / 消极这样的固定类别,应用场景很广。
IMDb 电影评论数据集是常用的情感分析数据集,训练集和测试集各 25000 条评论,正负标签各占一半。
预处理数据集的步骤是:词元化(拆成单词)、创建词表(过滤稀有词)、处理评论长度(统一成固定长度),最后转换成数据迭代器方便训练。
(注:文档部分内容可能由 AI 生成) 源地址