浅谈影评情感分析数据集的构建

前段时间国庆,回家休息了几天,每天熬夜玩手机,整个人算是有点颓废了。回来工作之后,渐渐地又过上了有规律的生活,说到底,还是自制力不够呀!本想着国庆的时候好好分析下影评数据,结果只是跑了个模型,其他啥也没干成,想想就真的有点浪费时间了。人生苦短,转眼间很多熟悉的人都结婚了,而自己却终究还是过不去那个坎。不过现在无所谓了,压力不是很大,抓紧时间不断学习和总结才是王道。言归正传,在国庆前,针对豆瓣的电影评论数据做了一个比较简单的情感分析,效果不是很好,最近又进行了进一步尝试,发现了一点点关于情感分析数据集的小门道,这里简单的总结下,后续做文本分析,或许还可以使用上。

往期回首

在9月底的时候,写了一篇有关情感分析的文章 豆瓣电影短评数据情感分析Baseline
,文章采用的数据集比较粗糙,笔者最开始采集的电影评论数据有4428475条,去掉RATING为NaN的数据之后,还剩4166704条。当时看着这416万数据,确实有点棘手,毕竟没有很好的服务器去跑模型。为此,做了一些数据清洗和过滤操作,包括长度过长、去重等操作,最后剩下了3582251条。评论中自带用户对电影的评分,分值为为1-5星(1-很差,2-较差,3-还行,4-推荐,5-力荐),所以最后笔者将评论划分为了三个:1-2星为消极negative(700572条),3星为正常neutral(1215485条),4-5星为正向positive(1666194条)。最后笔者也没有对数据进行采样,直接采用MNB进行多分类,最后各个class的平均precision和recall都接近0.6。效果不能说好,但也不能说非常差,毕竟也超过了0.5了。
国庆节当天在车上,思来想去,没理由这么差,回去之后仔细看了看数据集,发现数据集的区分度不是很好,主要的原因还是在于评分在2星、3星、4星的数据,很多意思口吻相近的数据,评分却不尽相同,比如

  1. “搞笑片哈哈哈哈哈哈哈哈哈”评分为2星,
  2. “好搞笑哈哈哈哈哈”评分是3星
  3. “很搞笑哈哈哈” 评分4星

仔细查阅了下,这种数据不只是上面这一种形式,当然还存在其他类型的,该怎么来做呢?

数据新探索

首先表示下,因为是自己构建数据集,当然想要弄一份比较好、数据质量高点的,那么什么才算质量高呢?坊间有这样一句话,“数据和特征决定了机器学习的上限,而模型和算法只是逼近这个上限而已”。也就是说,即使算法再不济,数据质量上去了,算法得到的结果都不会很差。有了这个念头,也就不管那么多了,首先在类别不调整的情况下,将1星归为negative,3星归为neutral,5星归为positive。如此之下,数据的区分度算是上去了。使用MNB训练之后,得到的结果差不多在0.68左右,效果比之前的0.6好了点,不过数据还是不纯,区分度不明显,主要在于3星的数据里面,有的倾向于negative,有的倾向于positive,这也就导致了模型训练之后,效果不佳。此时的数据量各个class的数据量差别还比较大,negative的24w,positive的51w,neutral的有117万,差距太大了。
考虑到后续要在自己单机上构建深度学习模型,所以在提高数据质量的同时,也要将数据量给降下去。说白了,就是以数量换取质量的意思,数据再多,杂乱无章也不是什么好事,如果有一份质量较高的数据,即使数据量降下来了,也还是说得过去的,何况数据量本来就比较多。再三思考之后,笔者做了最极端的做法,原本是三分类,直接改成了二分类,negative选择的是1星评论,positive选择的是5星评论。如此以来,区分度肯定是上去了。结果如何呢,接下来来看看结果。

探索下的结果

上面的都是想法,目的就是使得数据集各个类的区分度更加明显。有了这种想法之后,笔者就进行了进一步的验证。1星数据244912条,5星数据517218条,两倍多的差距,对于二分类来说数据集呈现出类别不均衡现象。所以,笔者进一步构建了训练集和测试机,训练集正负样本各220000条,测试集正负样本各24912条。之前取全部数据分3类跑MNB需要30min,去掉2星和4星的跑MNB需要16min左右,现在训练集44万数据,交叉验证训练时间大概5min不到,结果如下:

                precision    recall  f1-score   support

          -1       0.86      0.88      0.87     22073
           1       0.88      0.85      0.87     21927

    accuracy                           0.87     44000
   macro avg       0.87      0.87      0.87     44000
weighted avg       0.87      0.87      0.87     44000

CPU times: user 56.4 ms, sys: 2.12 ms, total: 58.6 ms
Wall time: 60.5 ms

对于测试集,预测结果也很不错,如下,平均都达到0.86,说明测试集与训练集的分布大致一样。

                precision    recall  f1-score   support

          -1       0.85      0.88      0.87     24912
           1       0.88      0.85      0.86     24912

    accuracy                           0.86     49824
   macro avg       0.86      0.86      0.86     49824
weighted avg       0.86      0.86      0.86     49824

这只是一个开始,简单的模型,未加任何参数调优过程,单纯是为了构造数据集。有这样的结果,确实挺满意的,后续对于中文文本分类的研究数据算是不用愁了吧!

结束语

笔者写这篇文章,主要是记录下自己构建数据的过程。实践证明,数据量并不是越多就越好,而是数据各个类别的区分度越高越好。数据量的增加对于模型来说,无疑是锦上添花,可以使模型的泛化能力得到很好的提升,但是区分度对于模型的精度来说也是至关重要,如果添加了一份比较杂乱无章的数据,还不如没有呢。OK,既然数据已经备好了,后续做模型也就省事了,虽然讲多分类变成了二分类,但整体上来说可行性还是可以的,都是个人实践,少个label也不是什么不可以的事情。关于情感分析,笔者会继续采用不同的算法进行剖析,后续也会将其做成服务,就当做是自己的一种实践方式吧!如有需要数据的,请关注[斗码小院]公众号,后台回复【情感分析数据集】即可。

References

  1. 豆瓣影评数据集: http://moviedata.csuldw.com
  2. http://www.csuldw.com
  3. https://scikit-learn.org