目录
- 数据介绍
- 数据清洗
- 对导入后的phone数据集进行清洗
- 对add_comments和 phone 进行数据合并,并尽心初步清洗
- 将处理后的数据存储为"处理后的数据.xlsx"
- 数据可视化
- 1. 淘宝在售手机价格区间统计
- 2. TOP10品牌 手机价格等级构成
- 3. 不同品牌手机现价&原价对比
数据介绍
查看数据详细信息
import pandas as pd
import numpy as np
import time
phone=pd.read_csv('cellphone.csv')
add_comments=pd.read_csv('count_add_comments.csv')
comments=pd.read_excel('comments.xlsx')
print(phone.info())
print(add_comments.info())
print(comments.info())
cellphone.csv的数据详细信息如下:
数据清洗
对导入后的phone数据集进行清洗
由上表,发现存在空白列,并且商品描述、月销量、库存、评分、累计评价数存在缺失值
- 删除空白列
phone=phone.drop(columns=['Unnamed: 19'])
- 先获取列名,在此基础上进行更改
phone.columns=['爬取时间', '爬取链接', '商品ID', '商品名称',
'商品描述', '商品参数', '商品现价',
'商品原价', '月销量', '库存',
'发货地址', '商品发布时间',
'店铺ID', '店铺名称', '商品链接URL', '评分',
'收藏数' ,'累计评价数', '商品评价印象标签']
- 将月销量、库存、累计评价数为null用0填充
phone['月销量']=phone['月销量'].fillna(0)
phone['库存']=phone['库存'].fillna(0)
phone['累计评价数']=phone['累计评价数'].fillna(0)
- 删除评分为null的样本
phone.dropna(subset=['评分'])
对add_comments和 phone 进行数据合并,并尽心初步清洗
对add_comments和 phone 进行数据合并
df=pd.merge(phone,add_comments,left_on='商品ID',right_on='ID(id)')
print(df.info())
合并数据如下:
6. 重命名并删除多余的列
df.columns=['爬取时间', '爬取链接', '商品ID', '商品名称',
'商品描述', '商品参数', '商品现价',
'商品原价', '月销量', '库存',
'发货地址', '商品发布时间',
'店铺ID', '店铺名称', '商品链接URL', '评分',
'收藏数' ,'累计评价数', '商品评价印象标签','图片', '追评', 'ID(id)', 'Unnamed: 3']
df=df.drop(columns=['Unnamed: 3'])
df=df.drop(columns=['ID(id)'])
- 清洗时间参数
df['商品发布时间']=df['商品发布时间'].apply(lambda op:time.strftime('%Y-%m-%d',time.localtime(op)))
- 清洗价格数据
def get_prices(s):
price=s.split('-')
l=[float(i) for i in price]
return np.mean(l)
df['商品现价']=df['商品现价'].apply(get_prices)
df['商品原价']=df['商品原价'].apply(get_prices)
- 清洗发货城市数据
pro_list=['北京',
'天津',
'上海',
'重庆',
'河北',
'山西',
'辽宁',
'吉林',
'黑龙江',
'江苏',
'浙江',
'安徽',
'福建',
'江西',
'山东',
'河南',
'湖北',
'湖南',
'广东',
'海南',
'四川',
'贵州',
'云南',
'陕西',
'甘肃',
'青海',
'台湾',
'内蒙古',
'广西',
'西藏',
'宁夏',
'新疆',
'香港',
'澳门']
def get_city(address):
for i in pro_list:
if i in address:
city=address.replace(i,'')
if len(city)==0:
city=i
return city
def get_province(address):
for i in pro_list:
if i in address:
province=i
return province
df['发货城市']=df['发货地址'].apply(get_city)
df['发货省份']=df['发货地址'].apply(get_province)
- 价格分箱
def get_price_level(p):
level=p//1000
if level==0:
return '0~999'
if level==1:
return '1000~1999'
if level==2:
return '1999~2999'
if level==3:
return '2999~3999'
if level==4:
return '3999~4999'
if level>=5:
return '5000+'
else:
return '计算出错'
df['价格等级']=df['商品现价'].apply(get_price_level)
- 手机参数信息提取
for t in target:
def get_parm(p):
for i in eval(p): # eval函数就是实现list、dict、tuple与str之间的转化
if i["label"]==t:
return i["value"]
df[t]=df['商品参数'].apply(get_parm)
将处理后的数据存储为"处理后的数据.xlsx"
df.to_excel('处理后的数据.xlsx')
数据可视化
导入数据,删除多余的列
import pandas as pd
import numpy as np
data=pd.read_excel('处理后的数据.xlsx')
data.drop(columns=['Unnamed: 0'],inplace=True)
删除价格异常的样本
# 计算下四分位数和上四分位
Q1 = data['商品现价'].quantile(q = 0.25)
Q3 = data['商品现价'].quantile(q = 0.75)
# 基于1.5倍的四分位差计算上下须对应的值
low_whisker = Q1 - 1.5*(Q3 - Q1)
up_whisker = Q3 + 1.5*(Q3 - Q1)
# 寻找异常点
data=data.drop(data['商品现价'][(data['商品现价']> up_whisker) | (data['商品现价'] < low_whisker)].index)
print(data)
1. 淘宝在售手机价格区间统计
sales=data['价格等级'].value_counts()
sales_bar=Bar()
sales_bar.add_xaxis(list(sales.index))
sales_bar.add_yaxis('价格等级',list(sales.values.astype(float)))
sales_bar.render('sales_bar.html')
结果如下:
由图可得,价格为1000~1999元的手机最多。
2. TOP10品牌 手机价格等级构成
进行数据集处理
#找出销售量top10的品牌
data1=data.groupby('品牌')['累计评价数'].sum().sort_values(ascending=False)[0:10]
# 从data数据集中挑出品牌为top10品牌的手机
data2 = pd.DataFrame(columns =data.columns.tolist())
for i in data1.index:
temp=data[data['品牌']==i]
data2=pd.concat([temp,data2]) # 向下拼接
scale1=data2[data2['价格等级']=='0~999'].groupby('品牌')['价格等级'].count().reset_index()
scale2=data2[data2['价格等级']=='1000~1999'].groupby('品牌')['价格等级'].count().reset_index()
scale3=data2[data2['价格等级']=='1999~2999'].groupby('品牌')['价格等级'].count().reset_index()
scale4=data2[data2['价格等级']=='2999~3999'].groupby('品牌')['价格等级'].count().reset_index()
scale5=data2[data2['价格等级']=='3999~4999'].groupby('品牌')['价格等级'].count().reset_index()
scale6=data2[data2['价格等级']=='5000+'].groupby('品牌')['价格等级'].count().reset_index()
scale_data=pd.merge(scale1,scale2,on='品牌',how='outer')
scale_data=pd.merge(scale_data,scale3,on='品牌',how='outer')
scale_data=pd.merge(scale_data,scale4,on='品牌',how='outer')
scale_data=pd.merge(scale_data,scale5,on='品牌',how='outer')
scale_data=pd.merge(scale_data,scale6,on='品牌',how='outer')
scale_data.columns=['品牌','0~999','1000~1999','1999~2999','2999~3999','3999~4999','5000+']
scale_data.fillna(0,inplace=True)
print(scale_data)
处理的结果集如下:
画出价格等级构成堆积图
duiji_bar=Bar(init_opts=opts.InitOpts(width='1200px',height='600px'))
duiji_bar.add_xaxis(scale_data['品牌'].tolist())
duiji_bar.add_yaxis('0~999',scale_data['0~999'].tolist(),stack='stack1')
duiji_bar.add_yaxis('1000~1999',scale_data['1000~1999'].tolist(),stack='stack1')
duiji_bar.add_yaxis('1999~2999',scale_data['1999~2999'].tolist(),stack='stack1')
duiji_bar.add_yaxis('2999~3999',scale_data['2999~3999'].tolist(),stack='stack1')
duiji_bar.add_yaxis('3999~4999',scale_data['3999~4999'].tolist(),stack='stack1')
duiji_bar.add_yaxis('5000+',scale_data['5000+'].tolist(),stack='stack1')
duiji_bar.set_series_opts(label_opts=opts.LabelOpts(is_show=False))
duiji_bar.set_global_opts(xaxis_opts=opts.AxisOpts(axislabel_opts={"rotate":25}))
duiji_bar.render("duiji_bar.html")
结果如下:
3. 不同品牌手机现价&原价对比
price1=data.groupby('品牌')['商品原价'].mean().reset_index()
price2=data.groupby('品牌')['商品现价'].mean().reset_index()
price=pd.merge(price1,price2,on='品牌')
compare_bar=Bar(init_opts=opts.InitOpts(width='1000px',height='600px'))
compare_bar.add_xaxis(list(price['品牌']))
compare_bar.add_yaxis('商品原价',list(np.round(price['商品原价'],2)),gap='20%',category_gap='50%')
compare_bar.add_yaxis('商品现价',list(np.round(price['商品现价'],2)),gap='20%',category_gap='50%')
compare_bar.set_global_opts(xaxis_opts=opts.AxisOpts(axislabel_opts={"rotate":90}))
compare_bar.set_series_opts(label_opts=opts.LabelOpts(is_show=False))
compare_bar.render('compare_bar.html')
结果如下:
由图形可得,华为品牌的手机,原价与现价相比,差距最大。