本次复习的知识点如下:
- 布尔型数组及数据过滤
- 多维数组的构造
- 使用numpy保存文本文件
- matplotlib折线图绘制
- matplotlib图表常用属性的设置方法
- 图表的保存
关于数据源
上次的文章发出之后发现忘了补充数据源的链接,之后咸鱼补充在留言区了,有需要动手实践的朋友可以自取,下面是直通车:
分析目标
观察上次的数据,数据中有的数据有会员与非会员两种用户类别。
这次我们主要分析一下两种类别用户的平均骑行时间对比。
数据读取与数据清洗
根据上次的流程示意图我们主要遵循下面几个步骤:
图 | 源自网络
但是在实际操作中发现,本次的实战数据非常干净,完全可以把我们的数据读取和数据清洗代码结合到一起来实现代码简化的目的。
此处代码可以简化为:
# 数据读取,数据清洗 def data_collection(): clndata_arr_list = [] for data_filename in data_filenames: file = os.path.join(data_path, data_filename) data_arr = np.loadtxt(file, skiprows=1, delimiter=',', dtype=bytes).astype(str) cln_data_arr = np.core.defchararray.replace(data_arr, '"', '') clndata_arr_list.append(cln_data_arr) return clndata_arr_list
在上一篇的文章中,具体的实现原理已经做过说明这里就不多做赘述。
数据分析
根据这次的分析目标,我们除了取出第一列的Duration (ms)
同时还要取出最后一列Member type
。
我们可以使用布尔型数组对我们的数据进行过滤,具体的使用方法可以参考下面这篇文章:
我们可以先看下完成后的这部分代码:
# 数据分析 def mean_data(clndata_arr_list, member_type): duration_mean_list = [] for cln_data in clndata_arr_list: bool_arr = cln_data[:, -1] == member_type filter_arr = cln_data[bool_arr] duration_mean = np.mean(filter_arr[:, 0].astype('float')/ 1000 / 60) duration_mean_list.append(duration_mean) return duration_mean_list
这里我们传入一个member_type
,用单个标量member_type
和取出的向量cln_data[:, -1]
做比较,以筛选出我们需要的数据。
在数学上标量和向量是没办法比对的,毕竟维度不同,但是在numpy中它的广播机制很好的为我们实现了这一需求,numpy可以将单个标量变成比对数据同样的数据维度,这样就可以进行一对一比对,达到使用布尔型数组筛选数据的需求了。
至于其余关于数据如何取出平均值等操作在上一篇文章已经做了介绍,接下来进入数据可视化展示的部分。
结果展示
生成的折线图:
生成的csv表格:
生成的数据图表上次美化不少,具体实现可以看下下面的代码,具体美化属性都标注在注释当中。
# 结果展示 def show_data(member_mean_duration_list, casual_mean_duration_list): # 构造多维数组 # 使用fmt方式输出指定格式的数据格式,默认输出科学计数的格式 mean_duraion_arr = np.array([member_mean_duration_list, casual_mean_duration_list]).transpose() np.savetxt('./mean_duration.csv', mean_duraion_arr, delimiter=',', header='Member Mean Duraion, Casual Mean Duraion', fmt='%.4f', comments='') # 生成空白画布 plt.figure() # color指定显示的折线颜色 # linestyle指定折线的样式 # marker指定节点样式 plt.plot(member_mean_duration_list, color='g', linestyle='-', marker='o', label='Member') plt.plot(casual_mean_duration_list, color='r', linestyle='--', marker='*', label='Casual') plt.title('Member vs Casual') # rotation指定下标的倾斜角度 plt.xticks(range(0, 4), ['1st', '2nd', '3rd', '4th'], rotation=45) # xlabel x,y轴的标题 plt.xlabel('Quarter') plt.ylabel('Mean duration (min)') plt.legend(loc='best') plt.tight_layout() plt.savefig('./duration_trend.png') plt.show()