机器学习 —— 数据分析与图表绘制

本文使用工具
       Anaconda下载安装与使用
       Jupyter Notebook的使用

本文使用数据集
      机器学习实验所需内容.zip


    以朝阳医院2018年销售数据为例,目的是了解朝阳医院在2018年里的销售情况,这就需要知道几个业务指标,本次的分析目标是从销售数据中分析出以下业务指标:
(1)业务指标1:月均消费次数
    月均消费次数 = 总消费次数 / 月份数(同一天内,同一个人所有消费算作一次消费)
(2)业务指标2:月均消费金额
    月均消费金额 = 总消费金额 / 月份数
(3)客单价
    客单价 = 总消费金额 / 总消费次数
(4)消费趋势(可视化展示,并根据可视化结果给出下属问题分析得出的结论)
    a、分析每天的消费金额
    b、分析每月的消费金额
    c、分析药品销售情况(截取销售数量最多的前十种药品,并用条形图展示结果)
    数据分析基本过程 数据分析基本过程包括:获取数据、数据清洗、构建模型、数据可视化以及消费趋势分析。

(一)数据获取

1. 读取数据,并且返回表格的前几行数据

import pandas as pd
# 读取数据(最好使用 object 类型读取)
data = pd.read_excel("朝阳医院2018年销售数据.xlsx", dtype="object")
# 通过panda模块内置的read_excel方法读取格式为.xlsx的excel表格内容,以object类型读取,还有一个为read_csv方法读取的是格式为.csv的Excel表格
data.head()# 返回data的前几行数据,默认为前五行,括号内部可填入数字表示显示几行数据

在这里插入图片描述图1:读取数据,并且返回表格的前几行数据

2. 修改为 DataFrame 格式,并且查看数据的形状

# 修改为 DataFrame 格式
dataDF = pd.DataFrame(data)# 定义一个dataDF来存储修改为DataFrame格式的数据
# DataFrame是一种表格型的数据结构。它的每一列可以是不同的值类型(例如布尔型、数值型、字符串等),
# 此外它既有行索引index,又有列索引columns。我们可以将它看成是由Series组成的字典(将每一列看成是一个Series)。
 
 # 查看数据的形状,即几行几列
print(dataDF.shape)# 形状(shape) 打印出数据的形状
print("dataDF.index:{}".format(dataDF.index))# 行索引(index) 打印出数据的参数

在这里插入图片描述图2:修改为 DataFrame 格式,并且查看数据的形状

3. 查看每一列的列表头内容

# 查看每一列的列表头内容
print("dataDF.columns:{}".format(dataDF.columns))# 打印出数据的每个列表头的说明,以及数据的类型
print(dataDF.columns)# 列索引(columns)

在这里插入图片描述图3:查看每一列的列表头内容

4. 查看每一列数据统计数目

# 查看每一列数据统计数目
# count()返回每一列中的非空值的个数。
print("dataDF计数:{}".format(dataDF.count()))

在这里插入图片描述图4:查看每一列数据统计数目

(二)数据分析

        数据清洗过程包括:选择子集、列名重命名、缺失数据处理、数据类型转换、数据排序及异常值处理。

1. 列名重命名

# 使用 rename 函数,把"购药时间" 改为 "销售时间"
dataDF.rename(columns={"购药时间": "销售时间"}, inplace=True)
# 通过rename函数对于数据的列名(columns)里面的购药时间改成销售时间,inplace:是否替换,默认为False。
# inplace为False时返回修改后结果,变量自身不修改。inplace为True时返回None,变量自身被修改。
print("dataDF.columns:{}".format(dataDF.columns))
# 打印出修改后的数据结果,以及数据类型

在这里插入图片描述

图5:列名重命名

2. 缺失值处理

# 删除缺失值之前
# 打印出数据缺失值之前的类型(几行几列)
print("删除缺失值之前dataDF.shape:{}".format(dataDF.shape))
# 使用dropna函数删除缺失值
# 因为Excel中的空的cell读入pandas中是空值(NaN),这个NaN是个浮点类型,一般当作空值处理,所以要先去除NaN再进行分隔字符串。
dataDF = dataDF.dropna()# 通过内置的dropna函数删除缺失的数据
# 删除缺失值之后
# 打印出缺失的数据被删除后的数据类型(几行几列)
print("删除缺失值之后dataDF.shape:{}".format(dataDF.shape))
# 将字符串转为浮点型数据
# 将销售数量,应收金额,实收金额的数据类型由字符串转变为浮点数类型(float)
# 数据类型转换:astype函数:字符串转换成数值(浮点型)
dataDF["销售数量"] = dataDF["销售数量"].astype("f8")
dataDF["应收金额"] = dataDF["应收金额"].astype("f8")
dataDF["实收金额"] = dataDF["实收金额"].astype("f8")
print("dataDF.dtypes:{}".format(dataDF.dtypes))
 

在这里插入图片描述

图6:缺失值处理

3. 数据类型转换之自定义函数

# 将日期进行分割
# 自定义函数::分隔销售口期,获取销售日期
# 输入:timeColSer销售时间这一列,是个Series数据类型
# 输出:分割后的时间,返回的也是Series数据类型
def splitsaletime(timeColser):
    timelist = []
    for t in timeColser:# [0]表示选取的分片,这里表示切割完后选取第一个分片
        timelist.append(t.split(" ")[0])# split(" ")分割
        timeser = pd.Series(timelist)# 将列表转行为一维数据Series类型
    return timeser

在这里插入图片描述

图7:数据类型转换之自定义函数

4. 数据类型转换之调用自定义函数

# 获取"销售时间"这一列数据
t = dataDF.loc[:, "销售时间"]# 获取销售时间这一列数据的数据存储到t里面
# 调用函数去除星期,获取日期
timeser = splitsaletime(t)# 对字符串进行分割,获取销售日期
# 修改"销售时间"这一列日期
dataDF.loc[:, "销售时间"] = timeser
print(dataDF.head())

在这里插入图片描述

图8:数据类型转换之调用自定义函数

5. 数据类型转换

# 字符串转日期
# errors='coerce'如果原始数据不符合日期的格式,转换后的值为NaT
dataDF.loc[:, "销售时间"] = pd.to_datetime(dataDF.loc[:, "销售时间"], errors='coerce')
# 将原本是字符串的日期类型转变成日期datatime类型的,pandas提供了一个可选的参数errors,
# 传入errors=‘coerce’,pandas遇到不能转换的数据就会赋值为NaN(Not a Number)
print("dataDF.dtypes:{}".format(dataDF.dtypes))

在这里插入图片描述

图9:数据类型转换

6. 删除空值

# 转换日期过程中不符合日期格式的数值会被转换为空值None,
 # 这里删除为空的行
dataDF = dataDF.dropna()
print("dataDF.shape:{}".format(dataDF.shape))
# 按销售时间进行升序排序
dataDF = dataDF.sort_values(by='销售时间', # by :按几列排序
                            ascending=True)# ascending=True为升序,ascending=False为降序
print("dataDF.head():{}".format(dataDF.head()))
# 重置索引(index)
dataDF = dataDF.reset_index(drop=True)
# 通过reset进行索引的重置,drop=True表示删除用作新索引的列,也就是删除被用作索引的第一列

在这里插入图片描述

图10:删除空值

7. 删除异常值

# 查看描述统计信息
# 描述指标:“销售数量”值不能小于0
print(dataDF.describe())
# 删除异常值:通过条件判断筛选出数据
# 将"销售数量"这一列中小于0的数排除掉
pop = dataDF.loc[:, "销售数量"] > 0
dataDF = dataDF.loc[pop, :]

在这里插入图片描述

图11:删除异常值

8. 删除重复数据

# 排除异常值后再次查看描述统计信息
print(dataDF.describe())
# 计算总消费次数
# 删除重复数据
kpi1_Df = dataDF.drop_duplicates(subset=['销售时间', '社保卡号'])
# drop_duplicates是pandas内的一个删除函数,subset:表示要进去重的列名,默认为 None。

在这里插入图片描述

图12:删除重复数据

(三)构建模型及数据可视化

        数据清洗完成后,需要利用数据构建模型(就是计算相应的业务指标),并用可视化的方式呈现结果。

1. 计算总消费次数

# 计算总消费次数
# 总消费次数:同一天内,同一个人发生的所有消费算作一次消费
# 有多少行
totall = kpi1_Df.shape[0]# 统计有多少行的数据(总消费次数)
print('总消费次数:', totall)
# 按销售时间升序排序
kpi1_Df = kpi1_Df.sort_values(by='销售时间', ascending=True)
# 对销售时间这一列进行升序排序,ascending=True为升序,ascending=False为降序
# 重命名行名(index)
kpi1_Df = kpi1_Df.reset_index(drop=True)

在这里插入图片描述

图13:计算总消费次数

2. 业务指标1-3(月均消费次数、月均消费金额、客单价)

# 获取时间范围
# 最小时间值
startTime = kpi1_Df.loc[0, '销售时间']
# 最大时间值
endTime = kpi1_Df.loc[totall - 1, '销售时间']
# 计算天数
daysI = (endTime - startTime).days
# 月份数:运算符"//"表示取整除,返回商的整数部分
monthsI = daysI // 30
print('月份数:', monthsI)

# 计算月均消费次数
# 业务指标1:月均消费次数=总消费次数 / 月份数
kpi1_I = totall // monthsI
print('业务指标1:月均消费次数=', kpi1_I)

# 总消费金额
totalMoneyF = dataDF.loc[:, '实收金额'].sum()
# 月均消费金额
# 业务指标2:月均消费金额 = 总消费金额 / 月份数
monthMoneyF = totalMoneyF / monthsI
print('业务指标2:月均消费金额=', monthMoneyF)

# 业务指标3:客单价 = 总消费金额 / 总消费次数
# 客单价(per customer transaction)是指商场(超市)每一个顾客平均购买商品的金额,客单价也即是平均交易金额。
pct = totalMoneyF / totall
print('业务指标3:客单价=', pct)

在这里插入图片描述

图14:月均消费次数、月均消费金额、客单价

3. 业务指标:消费趋势(可视化展示)

# 业务指标:消费趋势,画图-折线图
import matplotlib.pyplot as plt
from pylab import mpl # 画图时用于显示中文字符
mpl.rcParams['font.sans-serif'] = ['SimHei']   # SimHei是黑体的意思
# 在操作之前先复制一份数据,防止影响清洗后的数据
groupDf = dataDF
# 重命名行(index)为销售时间所在列的值
groupDf.index = groupDf['销售时间']
groupDf.head()

在这里插入图片描述

图15:重命名行(index)为销售时间所在列的值

4. a、分析每天的消费金额

# a、分析每天的消费金额
plt.figure(figsize=(20,10))# 设置画布大小
plt.plot(groupDf['实收金额'])
# plt.plot(x, y, format_string, **kwargs)可以绘制点和线, 并且对其样式进行控制
# x               X轴数据,列表或数组,可选
# y               Y轴数据,列表或数组
# format_string   控制曲线的格式字符串,可选
# kwargs          第二组或更多(x,y,format_string),可画多条曲线
plt.title('按天消费金额(ZShiJ)')# 设置图像标题
plt.xlabel('时间')    # 设置x轴的标签文本
plt.ylabel('实收金额')# 设置y轴的标签文本
plt.savefig("day.png")# 保存图片
plt.show()            # 把图像显示出来。

在这里插入图片描述图16:a、分析每天的消费金额

在这里插入图片描述
图17:按天消费金额

        分析:由图17按天消费金额,可以看出,每天的消费金额有所不同,但是除了极个别天会出现消费的金额较大,大部分人消费情况基本都在500元以内。

5. b、分析每月的消费金额

# b、分析每月的消费金额
# 将销售时间聚合按月分组
gb = groupDf.groupby(groupDf.index.month)
print(gb)

图18:b、分析每月的消费金额

图18:b、分析每月的消费金额

6. 描绘按月消费金额图

# 描绘按月消费金额图
# 对进行按月份分组好数据进行求和,从而看到每个月份的销售数量,应收金额,实收金额的数据和
monthDF = gb.sum()
print(monthDF)
# plt.figure(figsize=(8,7))# 设置画布大小
plt.plot(monthDF['实收金额'])# 根据实收金额绘制按月消费金额图的线图
plt.title('按月消费金额(ZShiJ)')# 设置图像标题
plt.xlabel('时间')      # 设置x轴的标签文本
plt.ylabel('实收金额')  # 设置y轴的标签文本
plt.savefig("month.png")# 保存图片
plt.show()              # 把图像显示出来。

在这里插入图片描述

图19:描绘按月消费金额图

在这里插入图片描述

图20:按月消费金额

        分析:由图20按月消费金额的结果显示,我们可以看出7月消费金额最少,我认为这是因为7月份的数据不完整,所以不具参考价值。

        1月、4月、5月和6月的月消费金额差异不大,2月和3月的消费金额迅速降低,这可能是2月和3月处于春节期间,大部分人都回家过年的原因。

7. c、分析药品销售情况(截取销售数量最多的前十种药品,并用条形图展示结果)

# c、分析药品销售情况(截取销售数量最多的前十种药品,并用条形图展示结果)
# 聚合统计各种药品的销售数量
# 对“商品名称”和“销售数量”这两列数据进行聚合为Series形式
medicine = groupDf[['商品名称','销售数量']]
# groupby按照商品名称进行分组,算出商品名称对应相应的销售数量
bk = medicine.groupby('商品名称')[['销售数量']]
# 按照商品名称对药品的销售数量进行求和
re_medicine = bk.sum()

在这里插入图片描述

图21:c、分析药品销售情况

8. 降序排序截取销售数量最多的十种药品

# 对药品销售数量按降序排序
re_medicine = re_medicine.sort_values(by='销售数量', ascending=False)# 降序排序
re_medicine.head()
# 截取销售数量最多的十种药品
top_medicine = re_medicine.iloc[:10,:]
print(top_medicine)

在这里插入图片描述
图22:降序排序截取销售数量最多的十种药品

9. 条形图展示销售数量前十的药品


# 用条形图展示销售数量前十的药品
# 对数据的top_medicine进行条形图的可视化
top_medicine.plot(kind = 'bar',color = 'pink')
plt.title('销售前十的药品(ZShiJ)')# 设置图像标题
plt.xlabel('药品')             # 设置x轴的标签文本
plt.ylabel('数量')             # 设置y轴的标签文本
plt.savefig("top_medicine.png")# 保存图片
plt.show()                     # 把图像显示出来。

在这里插入图片描述

图23:条形图展示销售数量前十的药品

在这里插入图片描述

图24:销售前十的药品

        分析:由图24销售前十的药品可以得到销售数量最多的前十种药品信息,这些信息将会有助于加强医院对药房的管理,比如多进一些销售数量多的药品。

异常问题与解决方案

问题1:去重复值用错函数
在这里插入图片描述

图25:没有成功去重复值

解决方案:Dropna是删除空值和缺失值,删除重复值需要使用drop_duplicates,drop_duplicates是pandas内的一个删除函数,subset:表示要进去重的列名,默认为 None。
在这里插入图片描述

图26:计算总消费次数

问题2:需要注意数据类型转换
在这里插入图片描述

图27:数据类型转换

解决方法:一定要记得将原始数据字符串格式日期转换成正常的数据日期,否则会影响后面建模。

参考资料

[1] 详解pandas最常用的3种去重方法
[2] Pandas常用函数大合集
[3] plt.plot()函数解析
[4] Pandas数据排序
[5] 可视化之用pandas绘制简单的图形


回到文章开头

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:/a/525557.html

如若内容造成侵权/违法违规/事实不符,请联系我们进行投诉反馈qq邮箱809451989@qq.com,一经查实,立即删除!

相关文章

Redis 和 Mysql 数据库数据如何保持一致性

1.1前言 我们在实际项目中经常会使用到Redis缓存用来缓解数据库压力,但是当更新数据库时,如何保证缓存及数据库一致性,一般我们采用延时双删策略。 目前系统中常用的做法是一个查询接口,先查询Redis,如果不存在则查询…

在展会上如何介绍产品和公司,柯桥俄语培训

1.Приглашаем Вас… 邀请您…… 2. Позвольте пригласить Вас… 请允许邀请您…… 3.Имеем честь пригласить Вас … 诚挚邀请您…… 4. Посылаем Вам приглашение на… 给您&#xff0…

性能优化 - 你能说一说,为什么做了骨架屏,FCP的指标还是没有提升吗

难度级别:中高级及以上 提问概率:80% FCP的全程是First Contentful Paint,是衡量网页性能的一个重要指标,很多人把FCP理解为元素内容首次渲染到浏览器上的时间。但由于现在比较流行的Vue或是React项目中,HTML文档最初只有一个id为app的DIV…

Qt使用iostream的cout

在QT想使用iostream的cout。 参考以下博客: (转载)Qt中使用cout输出的方法 pro里加上; CONFIG console勾选 Run in Terminal clean工程,重新构建 上面是cout的,下面是我的另一个函数的qDebug输出的。

上位机图像处理和嵌入式模块部署(qmacvisual之tcp客户端)

【 声明:版权所有,欢迎转载,请勿用于商业用途。 联系信箱:feixiaoxing 163.com】 视觉算法出了结果之后,一般都要通知到其他设备进行某些动作的。以前通信的方式,一般都是有线的,什么232、485、…

【Linux】HTTPS协议

HTTPS协议 1.什么是"加密"2.为什么要加密3.常见的加密方式4.数据摘要&&数据指纹5.数字签名6.理解链 - 承上启下7.HTTPS 的工作过程探究方案一:只使用对称加密方案二:只使用非对称加密方案三:双方都使用非对称加密方案四&am…

C顺序表:通讯录

目录 前言 通讯录数据结构 通讯录初始化 查找名字 增加联系人 删除联系人 展示所有联系人 查找联系人 修改信息 销毁通讯录 完整通讯录代码 前言 数据结构中的顺序表如果已经学会了,那么我们就可以基于顺序表来完成一个通讯录了 通讯录其实我们使用前…

项目运维方案资料-(word原件)31页

1. 文档介绍 2. 人员与责任 3. 运维过程内容 4. 运维资源 5. 运维服务规划保障 6. 事件处置 7. 质量改进 8. 运维边界及内容 软件开发管理全套资料获取方式①:点我获取 获取方式②:本文末个人名片直接获取。

SpringBoot快速入门笔记(5)

文章目录 一、elemetnUI1、main.js2、App.vue3、fontAwesome 一、elemetnUI 开源前端框架,安装 npm i element-ui -S 建议查看官方文档 Element组件,这里是Vue2搭配elementUI,如果是vue3就搭配elementPlus,这里初学就以Vue2为例子…

Matlab 基础语法 小结

input x input(prompt) # input digit str1 input(prompt,s) # input string执行图像处理任务 require Image Processing Toolbox Image Processing Toolbox™ provides a comprehensive set of reference-standard algorithms and workflow apps for image processing, a…

农业气象站的工作原理

TH-NQ8农田小气候监测站是一种专门用于监测农田内小范围气候状况的设备,其作用主要体现在以下几个方面: 实时监测与记录:通过配备的多种传感器,能够实时监测和记录农田内不同位置的气温、湿度、风速、风向、降雨量等气象要素的变化…

Android 9.0 framework层实现app默认全屏显示

1.前言 在9.0的系统rom产品定制化开发中,在对于第三方app全屏显示的功能需求开发中,需要默认app全屏显示,针对这一个要求,就需要在系统启动app 的过程中,在绘制app阶段就设置全屏属性,接下来就实现这个功能 效果图如下: 2.framework层实现app默认全屏显示的核心类 fram…

nginx配置实例-动静分离

目录 一、相关概念 1.1动静分离概念 1.2动静分离的两种实现方法 二、实例配置 2.1 准备工作:在linux系统中准备静态资源,方便后面做测试 2.2 修改nginx配置文件 2.3 在浏览器测试 一、相关概念 1.1动静分离概念 将动态请求跟静态请求分开&#xf…

下半年跨境电商全球市场持续扩大,掌握测评自养号技术将迎来新机遇

2024年跨境电商在下半年有望继续保持稳健增长,市场将更加国际化、便捷化和智能化,为消费者和卖家带来更多机遇和发展空间。 全球化市场持续扩大,随着全球市场的进一步开放和互联网的普及,跨境电商将继续拓展到更多的国家和地区。消…

使用aspose相关包将excel转成pdf 并导出

SpringBoot 项目 基于aspose相关jar包 将excel 转换成pdf 导出 1、依赖的jar包 &#xff0c; jar获取链接 aspose相关三方jar &#xff0c;下载解压后,在项目路径下建一个libs包&#xff0c;然后将下图两个jar 拷贝至刚新建的libs目录中 2、pom.xml中加入maven引入 <depend…

通用开发技能系列:Scrum、Kanban等敏捷管理策略

云原生学习路线导航页&#xff08;持续更新中&#xff09; 本文是 通用开发技能系列 文章&#xff0c;主要对编程通用技能 Scrum、Kanban等敏捷管理策略 进行学习 1.什么是敏捷开发 敏捷是一个描述软件开发方法的术语&#xff0c;它强调增量交付、团队协作、持续规划和持续学习…

具身智能机器人实现新里程碑!新型3D世界模型问世

随着人工智能技术的不断进步&#xff0c;视觉-语言-动作&#xff08;VLA&#xff09;模型在机器人控制、自动驾驶、智能助手等领域展现出了广阔的应用前景。这类模型能够将视觉、语言、动作等多模态信息进行融合&#xff0c;实现从感知到决策的端到端学习。然而&#xff0c;现有…

【Python基础】生成器

文章目录 [toc]什么是生成器生成器示例生成器工作流程生成器表达式send()方法和close()方法send()方法close()方法 个人主页&#xff1a;丷从心. 系列专栏&#xff1a;Python基础 学习指南&#xff1a;Python学习指南 什么是生成器 在Python中&#xff0c;使用生成器可以很方…

Longan Pi 3H 开发板体验

Longan Pi 3H 开发板体验 开箱内容 打开包装&#xff0c;你可以看到以下物品 一个Longan Pi 3H盒子Longan Pi 3H开发板 产品基本介绍 Longan Pi 3H 是基于 Longan Module 3H 核心板的 ARM Linux 开发板&#xff0c;以 H618 (Quad core ARM Cortex-A531.5Ghz , 64-bit) 为主控…

合并主分支到子分支

参考&#xff1a;【Git】合并分支出现 Please enter a commit message to explain why this merge is necessary.-CSDN博客 git 如何将主分支(master)合并到子分支上_git 将主分支合并到子分支-CSDN博客 1、先切换到主分支master git checkout master 2、把主分支代码拉到本地…