Task2 数据读取与数据分析

ryluo 2020-07-22 20:04:04

数据读取:

import pandas as pd 
import numpy as np
import matplotlib.pyplot as plt
import tensorflow as tf
import tensorflow.keras as keras
import matplotlib.pyplot as plt

data_path = '/data1/ryluo/TianChi/NLP/data/NLP_data_list_0715.csv'
trn_csv = '/data1/ryluo/TianChi/NLP/data/train_set.csv'
tst_csv = '/data1/ryluo/TianChi/NLP/data/test_a.csv'
sub_csv = '/data1/ryluo/TianChi/NLP/data/test_a_sample_submit.csv'

trn_data = pd.read_csv(trn_csv, sep='\t')
tst_data = pd.read_csv(tst_csv)
sub_data = pd.read_csv(sub_csv)
trn_data.shape
(200000, 2)
trn_data.head()
image-20200720153658775
tst_data.shape
(50000, 1)
tst_data.head()
image-20200720153836878
sub_data.head()
image-20200720153938207

数据分析:

trn_data['text_len'] = trn_data['text'].apply(lambda x: len(x.split(' ')))
trn_data['text_len'].describe()
count    200000.000000
mean        907.207110
std         996.029036
min           2.000000
25%         374.000000
50%         676.000000
75%        1131.000000
max       57921.000000
Name: text_len, dtype: float64
_ = plt.hist(trn_data['text_len'], bins=200)
image-20200720154027855
tst_data['text_len'] = tst_data['text'].apply(lambda x: len(x.split(' ')))
tst_data['text_len'].describe()
count    50000.000000
mean       909.844960
std       1032.313375
min         14.000000
25%        370.000000
50%        676.000000
75%       1133.000000
max      41861.000000
Name: text_len, dtype: float64
_ = plt.hist(tst_data['text_len'], bins=200)
image-20200720154103277

从上述的训练和测试数据的句子长度可视化可知,本次竞赛的文本长度都比较长,平均900多个词,并且训练和测试数据中的次的长度分布是差不多的。

trn_data['label'].value_counts().plot(kind='bar')
image-20200720154139003

在数据集中标签的对应的关系如下:{‘科技’: 0, ‘股票’: 1, ‘体育’: 2, ‘娱乐’: 3, ‘时政’: 4, ‘社会’: 5, ‘教育’: 6, ‘财经’: 7, ‘家居’: 8, ‘游戏’: 9, ‘房产’: 10, ‘时尚’: 11, ‘彩票’: 12, ‘星座’: 13}

从统计结果可以看出,赛题的数据集类别分布存在较为不均匀的情况。在训练集中科技类新闻最多,其次是股票类新闻,最少的新闻是星座新闻。

from collections import  Counter
all_lines = ' '.join(list(trn_data['text'])) # 将所有的文本拼接成一个连续的句子
word_count = Counter(all_lines.split(' ')) # word_count 返回的是一个字典
word_count = sorted(word_count.items(), key=lambda x: x[1], reverse=True)
print(len(word_count))#字符总数
print(word_count[0])  #出现最多的字符
print(word_count[-1]) #出现在最少的字符
6869
('3750', 7482224)
('3133', 1)

数据中总共的字符数量为6869,出现次数最多的为3750,出现次数最少的是3133

for i in range(10):
    print(word_count[i])
('3750', 7482224)
('648', 4924890)
('900', 3262544)
('3370', 2020958)
('6122', 1602363)
('4464', 1544962)
('7399', 1455864)
('4939', 1387951)
('3659', 1251253)
('4811', 1159401)

从字符出现最多的前10个字符的数量可以看出,’3750’ ‘648’ ‘900’相比于其他的字符出现的次数非常多,这里推测可能是标点符号

结论

  1. 类别不平衡
  2. 每个文本的字符数量非常大,属于长文本的文本分类问题

作业

  1. 假设字符3750,字符900和字符648是句子的标点符号,请分析赛题每篇新闻平均由多少个句子构成?
import re
trn_data['num_sen'] = trn_data['text'].apply(lambda x: len(re.split(r'3750|900|648', x)))
trn_data['num_sen'].describe()
count    200000.000000
mean         80.802370
std          86.955448
min           1.000000
25%          29.000000
50%          57.000000
75%         103.000000
max        3460.000000
Name: num_sen, dtype: float64
  1. 统计每类新闻中出现次数对多的字符
n_dict = {0:'科技', 1:'股票',  2:'体育', 3:'娱乐',  4:'时政', 5:'社会', 6:'教育', 
          7:'财经', 8:'家居',  9:'游戏', 10:'房产', 11:'时尚', 12:'彩票', 13:'星座'}

def get_max_word(df):
    all_lines = ' '.join(list(df['text']))
    w_c = Counter(all_lines.split(' '))
    s_tokens = ['3750','900', '648']
    for s in s_tokens:
        w_c.pop(s)

    w_c = sorted(w_c.items(), key=lambda x: x[1], reverse=True)
    return w_c[0]

for name, group in trn_data.groupby('label'):
    print(n_dict[name], ':',get_max_word(group))
科技 : ('3370', 503768)
股票 : ('3370', 626708)
体育 : ('7399', 351894)
娱乐 : ('6122', 187933)
时政 : ('4411', 120442)
社会 : ('6122', 159125)
教育 : ('6248', 193757)
财经 : ('3370', 159156)
家居 : ('6122', 57345)
游戏 : ('7328', 46477)
房产 : ('3370', 67780)
时尚 : ('4939', 18591)
彩票 : ('4464', 51426)
星座 : ('4939', 9651)