一. 数据观测(使用missingno 绘制缺失值矩阵)
- 生成一个缺失值矩阵,其中每个白色块表示缺失值的位置,非缺失值的位置则用深色块表示。通过观察矩阵,你可以快速了解每个变量中缺失值的情况
现在的数据是已经删除列全部为空,且空缺值大于90%,以及一些无用列的数据
import missingno as msno
msno.matrix(data)
删除空缺值,删除那些 列全部为空的列
data = data.dropna(axis = 1,how = "all")
#按照空缺的百分比删除(删除掉那些空缺值 大于 90% 的列)
data = data.drop(labels=data.columns[data.isnull().mean() >= 0.9],axis=1)
※ data.isnull().mean() #首先,先将每一列变成布尔类型,是空值为 True(1), else 为Fales(0),每一列求和,结果是空值数量,再除以每列行数,则计算出每列空值的比例
# 指定删除没有用的列
dropcols = ["链接","主图链接","主图视频链接","农药登记证号","农药生产许可证/批准文号",'农药产品标准证号','店铺类型','旺旺','下架时间','运费', '评价人数', '收藏人数','页码']
data.drop(columns=dropcols,inplace=True)
# 绘制
msno.matrix(data)
二.细分市场的基本情况
2.1 数据整理
# 选取 预估销售额 不为空的所有数据
data = data.loc[data.预估销售额.notnull()]
# 根据类别分类,然后对销售额进行求和,并且改名,且降序排列
d1 = pd.DataFrame(data.groupby(by="类别").预估销售额.sum()).rename(columns={"预估销售额":"销售额"}).sort_values(by="销售额",ascending=False)
#根据类别分类, 对销量进行求和,降序排列
d2 = pd.DataFrame(data.groupby(by="类别")["销量(人数)"].sum()).rename(columns={"销量(人数)":"销量人数"}).sort_values(by="销量人数",ascending=False)
# 销售额/销量人数 算出客单价
d3 = pd.DataFrame(d1.销售额.div(d2.销量人数),columns=["客单价"]).sort_values(by="客单价",ascending=False)
2.2 画图
# 一块空画布,返回值是
(<Figure size 4000x1200 with 2 Axes>,
array([<Axes: >, <Axes: >], dtype=object))
所有 fig:<Figure size 4000x1200 with 2 Axes
ax1是画布1, ax2 是画布2
fig,(ax1,ax2) = plt.subplots(nrows=1,ncols=2,figsize=(20,6))
# 5
xind = range(d1.shape[0]) #X轴索引
d1.plot(kind="bar",ax=ax1)
#这里的a是xind, b是一个列表,b[0]是销售额,b[1]是客单价
#d3.loc[d1.index] 因为d3跟d1 index 相同,d3使用d1的index,保存顺序一致
for a,b in zip(xind,list(zip(d1.销售额,np.round(d3.loc[d1.index].客单价, 2)))):
ax1.text(a-0.3,b[0],s=f"销售额:{b[0]}\n客单价:{b[1]}")
# autopct 是饼图中的数值
d2.plot.pie(subplots=True,ax=ax2,autopct="%.2f%%")
ax2.legend(loc=[-0.25,0.7])
三. 鼠类数据分析
3.1 数据处理
# 选取数据 类别都为 灭鼠的数据,且将所有空列删除
dfm = data.query("类别=='灭鼠'").dropna(axis=1,how="all")
#手动分50箱 1-500,每10个一组
bins = range(0,501,10)
# 生成价格区间列,将售价 步长为10 进行分箱
dfm["价格区间"] = pd.cut(dfm.售价,bins)
3.2竞争力 (人群 + 极致价值)
- 现有数据是 局部数据 进行竞争力分析
- 单个产品的平均销售额
- 单个产品的平均销售额最小值 (最大值)
- 不同价格区间 产品数量占比
- 1 - (单个产品平均销售额 - 单个产品的平均销售额最小值) / (单个产品的平均销售额最大值 - 单个产品的平均销售额最小值)
def byfunc(df,by="价格区间",sort="单个产品平均销售额"):
#计算销售额占比
res = df.groupby(by=by)[["预估销售额"]].sum()
#有些价格区间,没有产品,则可以去除
res = res.loc[res["预估销售额"] != 0]
#总计百分比
res["销售额占比"]=res["预估销售额"].div(res["预估销售额"].sum())
#每个价格区间中,产品的数量
res["产品数量"] = df.groupby(by=by)["宝贝ID"].nunique()
res["产品数量占比"]=res["产品数量"].div(res["产品数量"].sum())
#单个产品的平均销售额
res["单个产品平均销售额"] = res["预估销售额"].div(res["产品数量"])
#相对竞争力 结果指标
res["相对竞争力"] = 1-(res["单个产品平均销售额"] - res["单个产品平均销售额"].min())/(res["单个产品平均销售额"].max() - res["单个产品平均销售额"].min())
return res.sort_values(by=sort,ascending=False)
def plot(df):
axes = df.plot(y="相对竞争力",ls=":",marker="o",markerfacecolor="w",color="orange")
df.plot(kind="bar",y="销售额占比",ax=axes)
plot(byfunc(dfm))
四. 数据划分,归类(数据清洗)
4.1 物理形态
# a中文字空格分开, b是看 a有几个 数据,最后形成字典
def rep(str_=None,topla=None):
a = str_.split(" ")
b = [topla]*len(a)
return dict(zip(a,b))
nulldata.loc[nulldata.宝贝标题.str.contains("声波"),"物理形态"] = "驱鼠器"
nulldata.loc[nulldata.宝贝标题.str.contains("鼠板"),"物理形态"] = "粘鼠板"
nulldata.loc[nulldata.宝贝标题.str.contains("上门"),"物理形态"] = "服务"
nulldata.loc[nulldata.宝贝标题.str.contains("雾"),"物理形态"] = "液体"
nulldata.loc[nulldata.宝贝标题.str.contains("高压"),"物理形态"] = "驱鼠器"
nulldata.loc[nulldata.宝贝标题.str.contains("颗粒"),"物理形态"] = "固体"
nulldata.loc[nulldata.宝贝标题.str.contains("电"),"物理形态"] = "驱鼠器"
nulldata.loc[nulldata.物理形态.isnull(),"物理形态"] = "固体"
# 自己前面定义的rep,将 “,”前文字空格分开,b是看a里有几个,将所有的a进行替换
dfm.物理形态.replace(rep("胶水 胶水纸板 啫喱 油状 粘鼠板 粘胶 胶状 5个1元硬币厚硬板 胶板","粘鼠板"),inplace=True)
dfm.物理形态.replace(rep("固体 粉状","固态"),inplace=True)
dfm.物理形态.replace(rep("喷雾 气体 液体","液态"),inplace=True)
dfm.物理形态.replace(rep("8波段驱鼠器 声波 超声波物理驱鼠","驱鼠器"),inplace=True)
byfunc(dfm,by="物理形态")
4.2 地域
# 获取地域非空数据
dfm_ = dfm.loc[dfm.地域.notnull()]
# 地域是 "浙江 金华" 这种, 空格分开,如果 省份为空,返回城市,否则返回省份
dfm_["省份"] =dfm_.地域.str.split(" ").map(lambda x : x[1] if x[0]=="" else x[0])
# 如果长度为1,说明没有城市,省份当城市
dfm_["城市"] = dfm_.地域.str.split(" ").map(lambda x :x[0] if len(x)==1 else x[1])
# 按照省或市分割,目的去除省或者市
dfm_["省份"] = dfm_.省份.str.split("省|市").map(lambda x : x[0])
dfm_["城市"] = dfm_.城市.str.split("市").map(lambda x : x[0])
dfm_.loc[dfm_.省份=="苏州","省份"] = "江苏"
d = dfm_.groupby("省份").预估销售额.sum().reset_index()
#统一给所有的省 + 省字,市 + 市
def fo(x):
if x in ["上海","北京","天津","重庆"]:
return x +"市"
else :
return x + "省"
d.省份 = d.省份.map(fo)