基于神经网络的中文文本情感检测(二) 数据源获取及数据简单处理
- 时间:2020-04-30
- 529人已阅读
数据来源与获取
这里我已经准备好了你可以直接在我的网站上下载数据
1来自一个电商的评论数据包含6万多条其中消极积极评论各占一半左右
字段解释如下:
cat | label | review |
cat代表的被评价货物的类型 | 0 评论情感消极 ,1情感积极 | 评论内容 |
2微博评论情感标记数据集 链接:https://pan.baidu.com/s/1-FlAizp37vckgVWFjv48iw 提取码:a5cy
36 万多条,带情感标注 新浪微博,包含 4 种情感,其中喜悦约 20 万条,愤怒、厌恶、低落各约 5 万条
字段解释如下:
id | label | review |
文本id | 0喜悦 1愤怒 2厌恶 3低落 | 文本内容 |
数据解析
因为第一个数据集的label相对简单,所以我们先来用第一个数据集进行以后的工程(也即是以后的我们暂时用数据集一)
解析一下数据,这里你要安装csv这个python的csv文件解析库
""" 获取文件的分类文本以及情感 """ import csv with open('online_shopping_10_cats.csv','r',encoding="utf-8") as csvfile: reader = csv.reader(csvfile) all_items = [row for row in reader] reviews =[] car_type =[] label =[] review =[] for i in range(1,len(all_items)): car_type.append(all_items[i][0]) label.append(all_items[i][1]) review.append(all_items[i][2]) reviews.append(all_items[i])
我们看一看里面的数据
print(reviews[1]) print(car_type[1]) print(label[1]) print(review[1]) print(len(all_items)) print(len(label))
['书籍', '1', '作者真有英国人严谨的风格,提出观点、进行论述论证,尽管本人对物理学了解不深,但是仍然能感受到真理的火花。整本书的结构颇有特点,从当时(本书写于八十年代)流行的计算机话题引入,再用数学、物理学、宇宙学做必要的铺垫——这些内容占据了大部分篇幅,最后回到关键问题:电脑能不能代替人脑。和现在流行的观点相反,作者认为人的某种“洞察”是不能被算法模拟的。也许作者想说,人的灵魂是无可取代的。'] 书籍 1 作者真有英国人严谨的风格,提出观点、进行论述论证,尽管本人对物理学了解不深,但是仍然能感受到真理的火花。整本书的结构颇有特点,从当时(本书写于八十年代)流行的计算机话题引入,再用数学、物理学、宇宙学做必要的铺垫——这些内容占据了大部分篇幅,最后回到关键问题:电脑能不能代替人脑。和现在流行的观点相反,作者认为人的某种“洞察”是不能被算法模拟的。也许作者想说,人的灵魂是无可取代的。 62775 62774
这里因为标记为了方便使用的0和1来标记,我们需要写一个获取标签内容的函数
def get_label_text(label): if (label == "1"): return "积极" else: return "消极"
试着运行一下如下代码
get_label_text(label[1])
'积极'
数据简单处理
接下来我们来对数据进行简单的预处理处理内容包含如下
1 文本段落分词
2对分词后的词汇分别计数
3统计出积极消极文本中分词后词汇
4为了更直观我们将积极/消极的词汇比率转换为对数
文本段落分词
相比于英文分词只需要直接用空格,逗号,句号直接将句子分割为词汇不同。中文分词是一个非常麻烦的过程,为了实现中文分词我们要是用到jieba这个python库,如果你不是很会用这个库可以看一下我的博客的这一篇《jieba 分词的原理与使用》来了解jieba的分词使用。
这里直接将jieba分词封装成一个传入中文文本返回分词list的一个函数代码如下:
#中文分词比较麻烦 我们使用jieba分词 import jieba def get_zh_split(line): return list(jieba.cut(line, cut_all=False))
测试一下代码:
print(review[3]) get_zh_split(review[3])
作者在战几时之前用了"拥抱"令人叫绝.日本如果没有战败,就有会有美军的占领,没胡官僚主义的延续,没有战后的民发反思,没有~,就不会让日本成为一个经济强国.当然,美国人也给日本人带来了耻辱.对日中关系也造成了深远的影响.文中揭露了"东京审判"中很多鲜为人知的东西.让人惊醒.唉!中国人民对日本的了解是不是太少了. ['作者', '在', '战', '几时', '之前', '用', '了', '"', '拥抱', '"', '令人', '叫绝', '.', '日本', '如果', '没有', '战败', ',', '就', '有', '会', '有', '美军', '的', '占领', ',', '没胡', '官僚主义', '的', '延续', ',', '没有', '战后', '的', '民发', '反思', ',', '没有', '~', ',', '就', '不会', '让', '日本', '成为', '一个', '经济', '强国', '.', '当然', ',', '美国', '人', '也', '给', '日本', '人', '带来', '了', '耻辱', '.', '对', '日', '中', '关系', '也', '造成', '了', '深远', '的', '影响', '.', '文中', '揭露', '了', '"', '东京', '审判', '"', '中', '很多', '鲜为人知', '的', '东西', '.', '让', '人', '惊醒', '.', '唉', '!', '中国', '人民', '对', '日本', '的', '了解', '是不是', '太少', '了', '.']
接下来导入numpy以及用于计数的库文件然后创建三个计数对象(Counter)实例
#导入counter与numpy库 from collections import Counter import numpy as np # 创建三个Counter对象 用来对 positive, negative ,words计数 positive_counts = Counter() negative_counts = Counter() total_counts = Counter()
对分词后的词汇分别计数
现在开始对积极以及消极标签下的分词词汇分别计数
#循环所有单词在 reviews 中 然后分别计数 for i in range(len(review)): if(get_label_text(label[i]) == '积极'): for word in get_zh_split(review[i]): positive_counts[word] += 1 total_counts[word] += 1 else: for word in get_zh_split(review[i]): negative_counts[word] += 1 total_counts[word] += 1
测试一下
# 统计出 negative 中最常用的词汇 negative_counts.most_common()
[(',', 98652), ('的', 50300), ('了', 32768), ('。', 29995), ('!', 19686), (' ', 15380), ('是', 14920), ('我', 13790), ('不', 13239), ('都', 9746), ('就', 9151), ('也', 8410), ('买', 8206), (',', 7714), ('没有', 7265), ('还', 6578), ('很', 6426), ('在', 6348), ('有', 6037), ('说', 5434), ('酒店', 5203), ('?', 5006), ('京东', 4483), ('给', 4445), ('用', 4125), ('房间', 3966), ('.', 3865), ('好', 3781), ('这', 3777), ('没', 3751), ('一个', 3479), ('和', 3427), ('差', 3346), ('太', 3237), ('到', 3223), ('就是', 2952), ('、', 2728), ('不好', 2695), ('要', 2643), ('这个', 2636), ('什么', 2608), ('还是', 2540), ('不是', 2521), ('感觉', 2512), ('人', 2369), ('去', 2323), ('东西', 2298), ('又', 2261), ('可以', 2219), ('你', 2215), ('个', 2212), ('小', 2186), ('才', 2175), ('差评', 2155), ('知道', 2141), ('苹果', 2119), ('上', 2117), ('服务', 2044), ('…', 2040), ('垃圾', 2009), ('而且', 1995), .......]
# 统计出 positive中最常用的词汇 positive_counts.most_common()
[(',', 121486), ('的', 64887), ('。', 39999), ('了', 24446), ('很', 23895), ('好', 15406), (' ', 15058), ('是', 14250), ('不错', 14093), ('!', 13957), ('也', 12529), ('我', 10939), (',', 10153), ('还', 8764), ('在', 8112), ('都', 7304), ('买', 7287), ('有', 7218), ('就', 6376), ('酒店', 5992), ('可以', 5585), ('不', 5325), ('用', 5324), ('.', 5247), ('和', 5027), ('非常', 4755), ('、', 4738), ('没有', 4324), ('京东', 4270), ('房间', 4023), ('就是', 3934), ('喜欢', 3932), ('感觉', 3866), ('比较', 3690), ('这', 3633), ('还是', 3612), ('给', 3488), ('质量', 3444), ('到', 3442), ('服务', 3098), ('这个', 3035), ('一个', 2999), ('上', 2841), ('看', 2789), ('挺', 2724), ('苹果', 2687), ('人', 2671), ('说', 2578), ('我们', 2549) .......]
计算积极/消极分词后词汇的比率
pos_neg_ratios = Counter() #计算 positive 和 negative 使用最多的相同词汇的比率 # 考虑到同等使用相同的情况 单词至少出现100次 for term,cnt in list(total_counts.most_common()): if(cnt > 100): pos_neg_ratio = positive_counts[term] / float(negative_counts[term]+1) pos_neg_ratios[term] = pos_neg_ratio
测试一下
print("差评比率 = {}".format(pos_neg_ratios["差评"])) print("不错的比率 = {}".format(pos_neg_ratios["不错"])) print("非常的比率 = {}".format(pos_neg_ratios["非常"]))
差评比率 = 0.00046382189239332097 不错的比率 = 11.131911532385466 非常的比率 = 2.754924681344148
将积极/消极的词汇比率转换为对数
# 转换为对数 for word,ratio in pos_neg_ratios.most_common(): pos_neg_ratios[word] = np.log(ratio)
测试一下
print("差评比率 = {}".format(pos_neg_ratios["差评"])) print("不错的比率 = {}".format(pos_neg_ratios["不错"])) print("非常的比率 = {}".format(pos_neg_ratios["非常"]))
差评比率 = -7.6760099320288875 不错的比率 = 2.4098158964873897 非常的比率 = 1.0133901033361175
因为上面的比率是通过分词以后分别计数积极与消极的比值所以一个单词在积极中出现的越多在消极中出现的越少则这个词越偏向于积极(也就是比值大于一),当我们将比值转化为对数的时候就会发现转化以后为正值的词汇是越偏向于积极的负值则相反,ok我们测试一下这是不是和我们想的相同
# 带有“积极”标签的评论中最常见的词 pos_neg_ratios.most_common()[0:30]
[('挺舒服', 5.0172798368149243), ('感谢您', 4.7791234931115296), ('还会来', 4.1666652238017265), ('还来', 4.0073331852324712), ('很脆', 3.8607297110405954), ('物美价廉', 3.7376696182833684), ('棒棒', 3.6938669956249757), ('划算', 3.5539865908910926), ('脆甜', 3.5336865647082343), ('光临', 3.5312505099103531), ('杠杠', 3.5165082281731497), ('超值', 3.5098856874126563), ('实惠', 3.4746248502169728), ('棒', 3.312531744576499), ('物超所值', 3.2958368660043291), ('合身', 3.2896448957564082), ('一如既往', 3.2386784521643803), ('可口', 3.2268439945173775), ('囤货', 3.1527360223636558), ('感谢', 3.1516670751747506), ('大方', 3.1441522786722644), ('很棒', 3.1229940531649181), ('物有所值', 2.9806186357439426), ('周到', 2.9618307218783095), ('宝贝', 2.9473586892697754), ('一流', 2.9444389791664403), ('赞', 2.916998233011487), ('快乐', 2.810907586541918), ('出色', 2.7990219793079367), ('上身', 2.7932080094425169)]
# 在 "NEGATIVE" 标记中出现最频繁的词汇 list(reversed(pos_neg_ratios.most_common()))[0:30]
[('不近人情', -inf), ('太坑', -inf), ('一星', -inf), ('评差', -inf), ('差差', -inf), ('差评', -7.6760099320288875), ('骗子', -4.6347289882296359), ('垃圾', -4.2736854908779174), ('骗人', -4.2579739860039023), ('地摊货', -4.0775374439057197), ('无语', -4.0569887756783318), ('火龙果', -4.0018637094279352), ('再也不会', -3.9170105469391849), ('假货', -3.7216692769369271), ('玩意', -3.6951100038645723), ('骗', -3.6826098411003407), ('欺骗', -3.6763006719070761), ('没好', -3.5927355935610339), ('请问', -3.3945083935113587), ('差劲', -3.3426539260495449), ('假', -3.3418976393808637), ('别买', -3.3322045101752038), ('坑人', -3.240854731586976), ('最差', -3.239831190044189), ('上当', -3.2215389422876846), ('极差', -3.1074362631339922), ('恶心', -3.1016808515633718), ('太差', -3.0895751016643662), ('发霉', -3.0706335817271087), ('退货', -3.0038076875595365)]
看结果和我们想的基本相同
数据的简单处理就已经完成了至于如果你要数据可视化那你自己可以尝试一下将积极或者消极词汇做一个词云图,直方图,圆饼图等这个可以自由发挥了我就不画蛇添足了,下一篇再见啦。
相关文章:
1 . 基于神经网络的中文文本情感检测(五) 简单MLP网络的优化与模型保存
2 . 基于神经网络的中文文本情感检测(四) 开始构建简单的神经网络
3 . 基于神经网络的中文文本情感检测(三) 神经网络基础与发展历史
4 . 基于神经网络的中文文本情感检测(二) 数据源获取及数据简单处理
5 . 基于神经网络的中文文本情感检测(一) 检测目的及项目设计规划
6 . 各个实验室公开人脸数据集收集