0

0

Pandas数据重塑教程:高效堆叠多列的多种方法

心靈之曲

心靈之曲

发布时间:2025-11-19 13:52:14

|

681人浏览过

|

来源于php中文网

原创

Pandas数据重塑教程:高效堆叠多列的多种方法

本文详细介绍了在pandas dataframe中将多列堆叠并重塑为更简洁结构的三种高效方法。通过实例代码,分别演示了如何利用multiindex、`melt`与`pivot`组合以及`janitor`库的`pivot_longer`函数来实现数据从宽格式到长格式的转换,旨在帮助用户根据具体场景选择最合适的重塑策略,提升数据处理效率。

在数据分析和处理中,经常需要对DataFrame的结构进行调整,以适应不同的分析需求或模型输入。其中一个常见场景是将多个具有相似语义的列堆叠(stack)成少数几列,同时引入一个标识原始列来源的新列。例如,将包含左右侧(left_和right_)计数(_count)和总和(_sum)的列重塑为包含side、count和sum的更紧凑格式。

考虑以下初始DataFrame:

import pandas as pd

df = pd.DataFrame({
    'date': ['2023-12-01', '2023-12-05', '2023-12-07'],
    'other_col': ['a', 'b', 'c'],
    'right_count': [4, 7, 9],
    'right_sum': [2, 3, 5],
    'left_count': [1, 8, 5],
    'left_sum': [0, 8, 4]
})

print("原始DataFrame:")
print(df)

期望的输出格式如下:

         date other_col   side  count  sum
0  2023-12-01         a  right      4    2
1  2023-12-05         b  right      7    3
2  2023-12-07         c  right      9    5
3  2023-12-01         a   left      1    0
4  2023-12-05         b   left      8    8
5  2023-12-07         c   left      5    4

下面将介绍三种实现此重塑目标的方法。

方法一:利用MultiIndex和stack进行自定义重塑

这种方法通过巧妙地构建一个临时的MultiIndex(多级索引)来组织列,然后使用stack操作将数据从宽格式转换为长格式。

Smart Picture
Smart Picture

Smart Picture 智能高效的图片处理工具

下载
  1. 设置索引:首先,将不需要重塑的列(如date, other_col)设置为DataFrame的索引。
  2. 创建MultiIndex列:将剩余的列名(如right_count, left_sum)通过下划线_拆分,创建两级列索引,其中第一级表示side(如right, left),第二级表示度量类型(如count, sum)。
  3. 重命名列轴:为MultiIndex的列轴命名,使其更具可读性。
  4. 堆叠:使用stack('side')将第一级列索引(side)堆叠到行索引中。
  5. 重置索引:最后,将所有索引重置为列,并清理生成的列名。
out_multiindex = (df
    .set_index(['date', 'other_col']) # 1. 设置索引
    .pipe(lambda x: x.set_axis(x.columns.str.split('_', expand=True), axis=1)) # 2. 创建MultiIndex列
    .rename_axis(columns=['side', None]) # 3. 重命名列轴
    .stack('side') # 4. 堆叠'side'层
    .reset_index() # 5. 重置索引
)

print("\n方法一:使用MultiIndex和stack")
print(out_multiindex)

注意事项: 这种方法非常灵活,适用于列名具有清晰分隔符,并且需要将特定层级的列名转换为新列的场景。它要求对Pandas的MultiIndex操作有一定理解。

方法二:结合melt和pivot操作

melt和pivot是Pandas中进行数据重塑的两个核心函数,它们组合起来可以实现复杂的宽长格式转换。

  1. melt操作:首先,使用melt函数将所有需要重塑的列“融化”到一个新的value列中,同时创建一个side(这里暂时命名为var_name)列来存储原始的列名。
  2. 拆分列名:将melt生成的side列(如right_count)拆分为两部分:实际的side(right或left)和度量类型(count或sum)。
  3. pivot操作:最后,使用pivot函数,将拆分出的度量类型作为新的列名,value列的数据填充到这些新列中,并以date、other_col和side作为新的行索引。
  4. 重置索引和清理:重置索引并清理pivot操作可能留下的MultiIndex列名。
tmp = df.melt(['date', 'other_col'], var_name='temp_col') # 1. melt操作

# 2. 拆分列名
tmp[['side', 'col_type']] = tmp['temp_col'].str.split('_', n=1, expand=True)

out_melt_pivot = (tmp.pivot(index=['date', 'other_col', 'side'],
                            columns='col_type', values='value') # 3. pivot操作
                     .reset_index() # 4. 重置索引
                     .rename_axis(columns=None) # 清理列名
                 )

print("\n方法二:结合melt和pivot")
print(out_melt_pivot)

注意事项: melt和pivot是Pandas中非常常用的重塑工具,理解它们的工作原理对于处理各种数据格式至关重要。这种方法通常更易于理解和调试,因为它将重塑过程分解为几个逻辑步骤。

方法三:使用janitor库的pivot_longer函数

对于更复杂的重塑任务,或者当需要更简洁的语法时,可以考虑使用第三方库pyjanitor。它提供了类似R语言tidyr包的pivot_longer功能,能够以更声明式的方式处理宽长格式转换。

  1. 安装janitor:如果尚未安装,需要先安装pyjanitor库。
    pip install pyjanitor
  2. 导入janitor:在代码中导入janitor。
  3. 使用pivot_longer:指定不变的索引列(index),以及如何将原始列名映射到新的列(names_to)和如何解析原始列名(names_pattern)。names_pattern使用正则表达式来捕获列名的不同部分。
# pip install pyjanitor
import janitor

out_janitor = df.pivot_longer(index=['date', 'other_col'],
                              names_to=('side', '.value'),
                              names_pattern=r'([^_]+)_([^_]+)')

print("\n方法三:使用janitor库的pivot_longer")
print(out_janitor)

注意事项: janitor库的pivot_longer函数提供了强大的正则表达式匹配能力,使得处理具有复杂命名模式的列变得非常简单。.value占位符指示匹配到的部分应该直接作为新的列名,而不是作为新列的值。虽然引入了外部依赖,但对于频繁进行复杂重塑的用户来说,它可以显著提高代码的可读性和开发效率。

总结

本文介绍了在Pandas DataFrame中将多列堆叠并重塑为更简洁结构的三种主要方法:

  • MultiIndex与stack:适用于列名具有清晰分隔符,且希望通过构建多级列索引来灵活控制堆叠过程的场景。它提供了底层控制的强大能力。
  • melt与pivot组合:这是一种经典且通用的方法,通过将数据先“融化”再“透视”,分步实现重塑。它逻辑清晰,易于理解和调试,是Pandas数据重塑的基石。
  • janitor.pivot_longer:对于追求简洁和声明式语法的用户,特别是当列名模式复杂时,pyjanitor库提供的pivot_longer是一个非常高效且直观的选择,它利用正则表达式简化了列名解析过程。

选择哪种方法取决于具体的数据结构、个人偏好以及对库的熟悉程度。在实际应用中,建议根据数据的复杂性和团队的习惯,选择最适合的工具来高效完成数据重塑任务。

相关专题

更多
js正则表达式
js正则表达式

php中文网为大家提供各种js正则表达式语法大全以及各种js正则表达式使用的方法,还有更多js正则表达式的相关文章、相关下载、相关课程,供大家免费下载体验。

510

2023.06.20

正则表达式不包含
正则表达式不包含

正则表达式,又称规则表达式,,是一种文本模式,包括普通字符和特殊字符,是计算机科学的一个概念。正则表达式使用单个字符串来描述、匹配一系列匹配某个句法规则的字符串,通常被用来检索、替换那些符合某个模式的文本。php中文网给大家带来了有关正则表达式的相关教程以及文章,希望对大家能有所帮助。

248

2023.07.05

java正则表达式语法
java正则表达式语法

java正则表达式语法是一种模式匹配工具,它非常有用,可以在处理文本和字符串时快速地查找、替换、验证和提取特定的模式和数据。本专题提供java正则表达式语法的相关文章、下载和专题,供大家免费下载体验。

738

2023.07.05

java正则表达式匹配字符串
java正则表达式匹配字符串

在Java中,我们可以使用正则表达式来匹配字符串。本专题为大家带来java正则表达式匹配字符串的相关内容,帮助大家解决问题。

211

2023.08.11

正则表达式空格
正则表达式空格

正则表达式空格可以用“s”来表示,它是一个特殊的元字符,用于匹配任意空白字符,包括空格、制表符、换行符等。本专题为大家提供正则表达式相关的文章、下载、课程内容,供大家免费下载体验。

351

2023.08.31

Python爬虫获取数据的方法
Python爬虫获取数据的方法

Python爬虫可以通过请求库发送HTTP请求、解析库解析HTML、正则表达式提取数据,或使用数据抓取框架来获取数据。更多关于Python爬虫相关知识。详情阅读本专题下面的文章。php中文网欢迎大家前来学习。

293

2023.11.13

正则表达式空格如何表示
正则表达式空格如何表示

正则表达式空格可以用“s”来表示,它是一个特殊的元字符,用于匹配任意空白字符,包括空格、制表符、换行符等。想了解更多正则表达式空格怎么表示的内容,可以访问下面的文章。

232

2023.11.17

正则表达式中如何匹配数字
正则表达式中如何匹配数字

正则表达式中可以通过匹配单个数字、匹配多个数字、匹配固定长度的数字、匹配整数和小数、匹配负数和匹配科学计数法表示的数字的方法匹配数字。更多关于正则表达式的相关知识详情请看本专题下面的文章。php中文网欢迎大家前来学习。

528

2023.12.06

高德地图升级方法汇总
高德地图升级方法汇总

本专题整合了高德地图升级相关教程,阅读专题下面的文章了解更多详细内容。

0

2026.01.16

热门下载

更多
网站特效
/
网站源码
/
网站素材
/
前端模板

精品课程

更多
相关推荐
/
热门推荐
/
最新课程
AngularJS教程
AngularJS教程

共24课时 | 2.6万人学习

【李炎恢】ThinkPHP8.x 后端框架课程
【李炎恢】ThinkPHP8.x 后端框架课程

共50课时 | 4.4万人学习

Swoft2.x速学之http api篇课程
Swoft2.x速学之http api篇课程

共16课时 | 0.9万人学习

关于我们 免责申明 举报中心 意见反馈 讲师合作 广告合作 最新更新
php中文网:公益在线php培训,帮助PHP学习者快速成长!
关注服务号 技术交流群
PHP中文网订阅号
每天精选资源文章推送

Copyright 2014-2026 https://www.php.cn/ All Rights Reserved | php.cn | 湘ICP备2023035733号