Task01里边对赛题进行了分析,接下来进行数据读取与数据分析,通过使用Pandas库完成数据读取和分析操作。
1 数据读取
由赛题数据格式可知,可通过read_csv读取train_set.csv数据:
import pandas as pd
import numpy as np
import matplotlib.pyplot as plt#读取全量数据
train_df = pd.read_csv('./data/data45216/train_set.csv',sep='\t')
train_df.shape#读取部分数据
train_df = pd.read_csv('./data/data45216/train_set.csv',sep='\t',nrows=100)
train_df.shape
参数:sep每列的分隔符,用‘\t’分割,nrows=100,读取100条数据
Pandas还可以读取sql,excel,table,html,json等格式数据。
2 数据分析
2.1 计算新闻文本的长度
赛题数据中每行句子的字符使用空格进行分隔,可通过直接统计单词的个数得到每个句子的长度。
train_df['text_len'] = train_df['text'].apply(lambda x:len(x.split(' ')))
print(train_df['text_len'].describe())
由输出结果可知,句子的长度均值在907,最短的长度是2,最大的长度是57921:
查看句子长度的直方图:
_ = plt.hist(train_df['text_len'],bins=50)
plt.xlabel('Text char count')
plt.title('Histogram of char count')
输出结果:
2.2 查看赛题数据的类别分布
通过绘制直方图来查看每个新闻类别的分布。
train_df['label'].value_counts().plot(kind='bar')
plt.title('News class count')
plt.xlabel('category')
由输出结果可知,大部分的新闻分布是0,1,2,最少的是13,新闻的类别标识为:{‘科技’:0,‘股票’:1,‘体育’:2,‘娱乐’:3,‘时政’:4,‘社会’:5,‘教育’:6,‘财经’:7,‘家居’:8,‘游戏’:9,‘房产’:10,‘时尚’:11,‘彩票’:12,‘星座’:13}。
2.3 字符分布
统计每个字符出现的次数,将句子进行拼接进而划分为字符,并统计每个字符的个数。通过统计,知道3750,900,648的出现频率较高,可推测为标点符号。
from collections import Counter#将文本变为一个list
all_lines = ' '.join(list(train_df['text']))
print(len(all_lines))
#对每个词统计个数
word_count = Counter(all_lines.split(" "))
#进行排序
word_count = sorted(word_count.items(),key=lambda d:d[1], reverse = True)
print(len(word_count))
print(word_count[0])
print(word_count[-1])
使用Lambda函数,先对train_df['text']的数据进行去重,然后拼接统计:
train_df['text_unique'] = train_df['text'].apply(lambda x: ' '.join(list(set(x.split(' ')))))
all_lines = ' '.join(list(train_df['text_unique']))
word_count = Counter(all_lines.split(' '))
word_count = sorted(word_count.items(),key=lambda d:int(d[1]),reverse=True)
print(len(word_count))
print(word_count[0])
print(word_count[-1])
分析结论:
1.每个新闻的字符个数在900多,还有个别新闻较长,可能需要截断;
2.新闻类别分布不均匀,会影响模型精度。
3 作业
(1)假设字符3750,900,648是句子的标点符号,请分析每篇新闻平均由多少个句子构成?
一、利用for循环实现
flaglist1 = []
flaglist2 = []
flaglist3 = []
for i in range(train_df['text'].shape[0]):flag1,flag2,flag3 = train_df['text'].loc[i].split(' ').count('3750'),train_df['text'].loc[i].split(' ').count('900'),train_df['text'].loc[i].split(' ').count('648')flaglist1.append(flag1)flaglist2.append(flag2)flaglist3.append(flag3)
flaglist = list(map(lambda x:x[0]+x[1]+x[2],zip(flaglist1,flaglist2,flaglist3)))
train_df['flag_freq'] = flaglist
train_df['flag_freq'].mean()
二、用Counter实现
train_df['text_freq'] = train_df['text'].apply(lambda x: ' '.join(list(x.split(' '))))
print(len(train_df['text']))
# # #将文本变为一个list
strlist1 = []
strlist2 = []
strlist3 = []
for i in range(train_df['text_freq'].shape[0]):all_lines = train_df['text_freq'].loc[i]# #对每个词统计个数word_count = Counter(all_lines.split(' '))# print(word_count['3750'],word_count['900'],word_count['648'])strlist1.append(word_count['3750'])strlist2.append(word_count['900'])strlist3.append(word_count['648'])flaglist = list(map(lambda x:x[0]+x[1]+x[2],zip(strlist1,strlist2,strlist3)))
train_df['flag_freq'] = flaglist
train_df['flag_freq'].mean()
(2)统计每类新闻出现次数最多的字符
一、用groupby进行分组实现
groupdata = train_df.groupby(by=['label'])
print(groupdata.size())#每类新闻出现最多的词
max_freq = []
for i in range(len(groupdata.size())):df = groupdata.get_group(i)['text'].apply(lambda x: ' '.join(list(x.split(' '))))all_lines = ' '.join(list(df))word_count = Counter(all_lines.split(' '))del word_count['3750']del word_count['900']del word_count['648']word_count = sorted(word_count.items(),key=lambda d:int(d[1]),reverse=True)print(word_count[1][0])max_freq.append(word_count[1][0])
二、通过Pandas的类别数据实现
train_df['new_label'] = pd.cut(train_df['label'],[-1,0,1,2,3,4,5,6,7,8,9,10,11,12,13],labels=['0','1','2','3','4','5','6','7','8','9','10','11','12','13'])
train_df.set_index('new_label').sort_index(ascending=False).head()max_freq = []
for i in range(14):df = train_df[train_df['new_label']==str(i)]['text'].apply(lambda x: ' '.join(list(x.split(' '))))all_lines = ' '.join(list(df))word_count = Counter(all_lines.split(' '))del word_count['3750']del word_count['900']del word_count['648']word_count = sorted(word_count.items(),key=lambda d:int(d[1]),reverse=True)print(word_count[1][0])max_freq.append(word_count[1][0])
思考:如何解决类别不均衡问题?