金牌厨师Pandas:听说Excel处理数据分行快得很?

HeoiJin 凹凸数据

大家好,我是HeoiJin

作者简介:立志透过数据看清世界的产品策划,专注爬虫、数据分析、产品策划领域。
万物皆营销 | 资本永不眠 | 数据恒真理
CSDN:https://me.csdn.net/weixin_40679090

一、前言

最近收到一个小朋友(无中生友)发过来的需求,要将多列数据转化成多行数据,并提取指定列的数据。

但因为数据结构有点丑,而且数据量大,不好通过excel公式进行清洗,希望我利用python帮他清洗下。

那么这位小朋友碰上了什么幺蛾子,接下来一起一探究竟吧。

二、项目准备

语言:Python 3.7
IDE:Pycharm
相关库:Pandas、re、xlrd、xlwt

三、项目特色

利用ExcelFile方法读取单个Excel文件中的多个sheets

利用explode方法为dataframe中嵌套的列表解嵌套为多行数据

四、项目需求

拿到样本数据和最终效果图的那一刻,有句话想跟设计表格的大佬说,不知当讲不当讲...各位先品一品这堆数据。

吐槽归吐槽,金牌厨师胖大师表示:“这波问题不大,接下来我要展示我王者水平的操作!”

(点击可放大本图)

五、核心厨具介绍

pandas.DateFrame.explode能将dataframe的嵌套列表拆分成多行,并会复制同一行的其他元素。

六、烹饪开始

6.1 确认烹饪思路

  1. 遍历所有sheet
  2. 筛选出核心的房号、姓名、电话信息
  3. 将信息拼接成为列表
  4. 将列表拆分为多行数据
  5. 输出为csv

6.2 筛选核心食材(获取特定的columns)

观察可知,三个sheets的表头顺序都不一样,如果只利用简单粗暴的切片方式,并不能精准地获取到需要的表头。但庆幸表头名称都相同,派出正则表达式这把利刃便能轻松地完成任务。

def get_new_columns(df):    '''    >> 利用正则匹配出目标columns    >> df.columns=['栋数', '户型', '姓名', '性别', '电话', '房号', '姓名.1', '性别.1', '电话.1', '房号.1','姓名.2', '性别.2', '电话.2', '房号.2']    >> 当我们的columns重复的时候,pandas会自动帮我们在重复的columns后面加上.编号。    :param df:    :return:    '''    # 提取columns对应的字段    pattern_name=r',(姓名.?\d?),'    pattern_room=r',(房号.?\d?),'    pattern_phoone=r',(电话.?\d?),'    # 通过前后增加逗号,确保正则的精准匹配    columns_str=','+','.join(df.columns.to_list())+','    columns_name=re.findall(pattern_name,columns_str)    columns_room=re.findall(pattern_room,columns_str)    columns_phone=re.findall(pattern_phoone,columns_str)    target_columns=[]    # 将每一行的数据变为一个一层嵌套的列表    for i in range(len(columns_name)):        target_columns+=[columns_room[i],columns_name[i],columns_phone[i]]    return target_columns

6.3 调制酱料(多列数据合并为一列)

这里定义一个函数,用于将每行的元素合并成一个有一层嵌套列表的series。

# 用于rebuild_df的applydef merge_cols(Series):    # 获取非空项    Series=Series[Series.notna()]    # 获取当行所有数据    value=Series.values    result=[]    # 将每一行的数据变为一个一层嵌套的列表    for idx in range(0,len(value),3):        result.append([value[idx],value[idx+1],value[idx+2]])    return result

6.4 大火爆炒,加料调味(拆分嵌套为多行,拼接其他数据)

食材和配料我们都准备好了,下面就可以开火下锅制作佳肴

烹饪流程:

  1. 获取楼层、户型信息
  2. 利用apply方法,拼接每行数据
  3. 利用explode方法展开数据
  4. 拆分每组数据
def rebuild_df(df,merge_columns):    # 获取表格头部通用信息    # merge_columns=['房号', '姓名', '电话', '房号.1', '姓名.1', '电话.1', '房号.2', '姓名.2', '电话.2']    df_new=df.iloc[:,:2]    # 调用merge_cols函数对数据进行合并    # 注意:使用apply调用函数时不用加括号    df_new['merge']=df.loc[:,merge_columns].apply(merge_cols,axis=1)    # 通过explode变成多行    df=df_new.explode('merge')    # 拆分merge列的列表    df['房号']=df['merge'].str[0]    df['姓名']=df['merge'].str[1]    df['电话']=df['merge'].str[2]    df.drop('merge',axis=1,inplace=True)    return df

6.5 跑堂的,上菜!

我们的食材有多个sheets,通过ExcelFile方法读取所有sheets名,并在输出的文件名中添加sheets名来区分文件。

def open_file(sheets_name):    df=pd.read_excel('数据集/多行转多列数据集.xlsx',sheet_name=sheets_name)    return dfif __name__ == '__main__':    sheets_name_list=pd.ExcelFile('数据集/多行转多列数据集.xlsx').sheet_names    for sheets_name in sheets_name_list:        df=open_file(sheets_name)        merge_columns=get_new_columns(df)        df=rebuild_df(df,merge_columns)        df.to_excel(f'数据集/{sheets_name}.xls', index=False,sheet_name=sheets_name,encoding='utf-8')

ok,数据非常快就清洗完了,打开其中一个表格检查下效果,小老板搞得不丑~

七、后记

本文核心思路:

  • 利用ExcelFile读取多个sheet
  • 通过explode方法,将横版的数据转换为竖版

完整代码及数据集请移步至文末github地址或阅读原文

(PS.数据集为脚本随机生成的虚拟数据)

后续将推出一篇食材来自”垃圾场“的清洗实战,究竟都多脏?

先看看群友们对这份数据的看法吧~

欲知后事如何,请您下回分解~
github地址:https://github.com/heoijin/Date-Clean

参考资料:
pandas原文档:
https://pandas.pydata.org/pandas-docs/stable/reference/api/pandas.DataFrame.explode.html

©著作权归作者所有:来自51CTO博客作者mb5fe18e5a55d8d的原创作品,如需转载,请注明出处,否则将追究法律责任

更多相关文章

  1. Oracle19c_cdb数据库自动安装部署脚本
  2. 超全的pandas数据分析常用函数总结:下篇
  3. 手把手带你爬天猫,获取杜蕾斯评论数据
  4. 用python分析1225万条淘宝数据,终于搞清楚了我的交易行为
  5. 超全的pandas数据分析常用函数总结:上篇
  6. 没有食材,数据分析师如何做饭?
  7. python入门教程12-06 (python语法入门之进程间数据隔离)
  8. 数据结构 #2 36张图带你深刻理解链表
  9. 数据结构 #1 浅谈数组

随机推荐

  1. Android(安卓)Studio的基本控件 图片框与
  2. Android中自动朗读(TTS)的简单使用
  3. Android 插件化 动态升级
  4. Android(安卓)WebView的加载超时处理
  5. AndroidManifest.xml文件剖析
  6. android Aspectj实践问题
  7. android 一个很漂亮的控件ObservableScro
  8. Android性能调优总结
  9. 简析Android对Linux内核的改动
  10. Android开发秘籍学习笔记(八)