首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >列上带条件的pandas多索引选择

列上带条件的pandas多索引选择
EN

Stack Overflow用户
提问于 2020-01-10 01:08:22
回答 2查看 53关注 0票数 4

我在过滤多索引数据帧时遇到了问题。

代码语言:javascript
复制
import numpy as np
import pandas as pd
df = pd.DataFrame(np.random.randn(6, 6), 
  columns=pd.MultiIndex.from_arrays((['Team_1','Team_1','Team_1','Team_1','Team_1','Team_1'],
  ['A','A','A','B','B','B'], ['a', 'b', 'c', 'a', 'b', 'c'])))

看起来是这样的:

代码语言:javascript
复制
     Team_1                                                  
          A                             B                    
          a         b         c         a         b         c
0  1.663478  1.121481 -0.675905 -1.286932 -0.713381  0.835101
1  0.076587  1.334063 -1.804435 -0.892450 -0.349493 -1.448643
2  0.485618  0.675481 -0.488584 -0.354583  1.827532 -1.184389
3 -0.531397 -0.145830 -1.143331 -0.871459 -0.009081 -1.741627
4  0.355948 -2.275475  0.543201 -0.099087 -1.114334 -1.248298
5  1.448409 -0.974127  2.004364 -0.880845  1.195134  0.392949

我想要的是输出一个df,其中ab有一些要求,如果两者都为真,那么也包括c列。例如,给定切分a>0b<0的输出如下所示

代码语言:javascript
复制
     Team_1                                                  
          A                             B                    
          a         b         c         a         b         c
0  1.663478       NaN       NaN       NaN -0.713381       NaN
1  0.076587       NaN       NaN       NaN -0.349493       NaN
2  0.485618       NaN       NaN -0.354583       NaN       NaN
3       NaN -0.145830       NaN       NaN -0.009081       NaN
4  0.355948 -2.275475  0.543201       NaN -1.114334       NaN
5  1.448409 -0.974127  2.004364       NaN       NaN       NaN

首先,我可以执行基本的选择(df.iloc[:, df.columns.get_level_values(2) == 'a'] > 0),但不确定从哪里开始。

EN

回答 2

Stack Overflow用户

回答已采纳

发布于 2020-01-10 03:02:23

另一种选择是使用stack/unstack

代码语言:javascript
复制
result = (
    df.stack(level=[0, 1])
      .assign(
          c=lambda df: np.where(
              (df["a"] > 0) & (df["b"] < 0),
              df["c"], np.nan
          )
          a=lambda df: np.where(
              df["a"] > 0, df["a"], np.nan
          ),
          b=lambda df: np.where(
              df["b"] < 0, df["b"], np.nan
          )
      ).unstack(level=[1, 2])
      .reorder_levels([1, 2, 0], axis=1)
      .sort_index(level=1, axis=1)
)

如果我们从一个看起来像这样的df开始:

代码语言:javascript
复制
     Team_1                                                  
          A                             B                    
          a         b         c         a         b         c
0  0.622728 -1.059337  0.154738 -1.118633  0.336635  1.173941
1  0.166443  0.236547  0.690746  0.169085 -0.107237 -0.539768
2 -1.270542  0.525559  0.335747  0.455872 -0.523938  0.508105
3  1.964184  0.281073  0.567805  0.012256  2.773986 -0.900674
4  1.997804 -0.621523 -0.253128  1.867092  0.134846  2.729482
5  0.860470 -0.293951 -1.581081 -2.014744  1.357025 -1.007692

输出result将为:

代码语言:javascript
复制
     Team_1                                                  
          A                             B                    
          a         b         c         a         b         c
0  0.622728 -1.059337  0.154738       NaN       NaN       NaN
1  0.166443       NaN       NaN  0.169085 -0.107237 -0.539768
2       NaN       NaN       NaN  0.455872 -0.523938  0.508105
3  1.964184       NaN       NaN  0.012256       NaN       NaN
4  1.997804 -0.621523 -0.253128  1.867092       NaN       NaN
5  0.860470 -0.293951 -1.581081       NaN       NaN       NaN
票数 2
EN

Stack Overflow用户

发布于 2020-01-10 01:27:01

使用xs选择列并删除该级别的MultiIndex。然后,'c'是前两个掩码之间的&检查。使用keys使用concat添加标签,然后使用这个完整的布尔掩码对原始DataFrame进行子集。

代码语言:javascript
复制
m1 = df.xs('a', level=2, axis=1).gt(0)  # a > 0
m2 = df.xs('b', level=2, axis=1).lt(0)  # b < 0
m = pd.concat([m1, m2, m1&m2], axis=1, keys=['a', 'b', 'c']).reorder_levels([1,2,0], axis=1)

df[m]   # used np.random.seed(13) in creation.
     Team_1                                            
          A                             B              
          a         b         c         a         b   c
0       NaN       NaN       NaN  0.451812       NaN NaN
1  1.350188       NaN       NaN       NaN -0.788989 NaN
2  0.562847 -0.243326  0.913741  0.317351       NaN NaN
3  0.606289 -0.026772 -0.984161  1.190705       NaN NaN
4       NaN       NaN       NaN       NaN       NaN NaN
5  0.490872       NaN       NaN       NaN       NaN NaN
票数 2
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/59668982

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档