为了账号安全,请及时绑定邮箱和手机立即绑定

python pandas 过滤器函数正则表达式在 MultiIndex 数据帧上的行为

python pandas 过滤器函数正则表达式在 MultiIndex 数据帧上的行为

呼如林 2023-02-15 17:15:50
tag这是一个带有索引和 的MultiIndex 数据透视表uom。tag我的目标是使用正则表达式和过滤函数按索引过滤行。例如:df.filter(regex="^Assets$", axis="index")理想情况下会过滤掉该行:fy                                                              2018          2019                                      tag                                                uom                                                                  Assets                                             USD  3.753190e+11  3.385160e+11  但是,当我这样做时,它会输出一个空数据框:Empty DataFrame                                                                                                         Columns: [2018, 2019]                                                                                                   Index: []我能够通过使用来规避这个问题:df.index.get_level_values("tag").str.contains("^Assets$")或者作为一个函数search = lambda df, regex, index_name: df.loc[df.index.get_level_values(index_name).str.contains(regex)]但这对我来说不太令人满意。我是否遗漏了有关 pandas 过滤器功能及其正则表达式输入如何工作的信息?它没有按预期运行,我的猜测是因为我有 2 个索引:tag因此当我用作我的正则表达式时uom,正则表达式在索引中失败。uom"^Assets$""^Assets$|USD"这是通过使用返回整个数据帧的正则表达式来支持的,因为所有行都有uom=USD,并且它表明过滤器函数将两个索引都考虑在内。如果是这种情况,那么我如何有选择地tag为 MultiIndex 数据帧上的过滤器函数选择 index= ?
查看完整描述

3 回答

?
白衣非少年

TA贡献1155条经验 获得超0个赞

过滤器函数的正则表达式部分的实现很短,很容易适应多索引场景,在这种情况下您仍然希望只使用多索引的正则表达式 1 部分。我知道这不是对您所问内容的直接回答,因为您是对的,因为实现的过滤器功能不处理多索引。


我在这里遇到了同样的问题,并认为发布我使用过的代码(改编自 pandas 原始代码)可能对其他人来说是一个有用的答案:


import regex as re


def filter_multi(df, index_level_name, regex, axis=0):

    def f(x):

        return matcher.search(str(x)) is not None


    matcher = re.compile(regex)

    values = df.axes[axis].get_level_values(index_level_name).map(f)

    return df.loc(axis=axis)[values]

使用附录中的代码:


print(df)

print(filter_multi(df, index_level_name='tag', regex='^Assets$', axis=0))

print(filter_multi(df, index_level_name='fy', regex='^2019$', axis=1))


查看完整回答
反对 回复 2023-02-15
?
炎炎设计

TA贡献1808条经验 获得超4个赞

另一种选择是首先uom从您的索引中删除,应用filter(然后将其应用于唯一的索引tag)并添加uom回您的索引,如

df.reset_index('uom').filter(regex="^Assets$", axis=0).set_index('uom', append=True)


查看完整回答
反对 回复 2023-02-15
?
守候你守候我

TA贡献1802条经验 获得超10个赞

如果你想从多索引的第一部分过滤一个唯一值,你可以使用loc

df.loc[['Assets']]

这使:

fy                  2018          2019
tag    uom                            
Assets USD  3.753190e+11  3.385160e+11

如果对于你的实际问题,必须使用过滤器,你应该重置索引未使用的部分并在过滤后将其设置回去:

df.reset_index(level='uom').filter(regex='^Assets$', axis=0).set_index('uom', append=True)


查看完整回答
反对 回复 2023-02-15
  • 3 回答
  • 0 关注
  • 201 浏览
慕课专栏
更多

添加回答

举报

0/150
提交
取消
微信客服

购课补贴
联系客服咨询优惠详情

帮助反馈 APP下载

慕课网APP
您的移动学习伙伴

公众号

扫描二维码
关注慕课网微信公众号