【问题标题】:Unable to subset Pandas dataframe无法对 Pandas 数据框进行子集化
【发布时间】:2016-09-14 20:15:26
【问题描述】:

我在名为in_file的数据框中有以下数据:

Client  Value_01   Value_02   Date
ABC     100       500       2016-09-01T
ABC     14        90        2016-09-02T
DEF     95        1000      2016-09-01T
DEF     200       600       2016-09-02T
GHI     75        19        2016-09-01T
GHI     300       700       2016-09-02T
JKL     50        02        2016-09-01T
JKL     400       800       2016-09-02T

我使用以下内容对数据框进行子集化(我们将其称为“子集 1”):

df_01 = in_file.loc[(in_file.Date == '2016-09-01T') & (in_file.Client <> 'ABC') & (in_file.Client <> 'DEF')].sort_values('Value_01', ascending=False)

我回来了:

Client  Value_01   Value_02   Date
GHI     75        19        2016-09-01T
JKL     50        02        2016-09-01T

然后,我尝试使用以下内容对数据框进行子集化(我们将其称为“子集 2”):

df_02 = in_file.loc[(in_file.Date == '2016-09-01T') & (in_file.Client == 'ABC') & (in_file.Client == 'DEF')].sort_values('Value_01', ascending=False)

使用“子集 2”,我得到一个空数据框。但是,我期待看到以下内容:

Client  Value_01   Value_02   Date
ABC     100       500       2016-09-01T
DEF     95        1000      2016-09-01T

有谁知道为什么“子集 2”代码没有返回我期望的数据框?

提前致谢。

【问题讨论】:

  • 你想要(in_file.Client == 'ABC') &amp; (in_file.Client == 'DEF') 吗?两者同时为真?
  • 试试这个:in_file.loc[(in_file.Date == '2016-09-01T') &amp; (in_file.Client.isin(['ABC', 'DEF'])].sort_values('Value_01', ascending=False)
  • 是否有与isin 对应的允许我排除某些数据的方法?

标签: python pandas subset


【解决方案1】:

包括isin():

In [28]: in_file.loc[(in_file.Date == '2016-09-01T') & in_file.Client.isin(['ABC', 'DEF'])].sort_values('Value_01', ascending=False)
Out[28]:
  Client  Value_01  Value_02         Date
0    ABC       100       500  2016-09-01T
2    DEF        95      1000  2016-09-01T

排除:

In [29]: in_file.loc[(in_file.Date == '2016-09-01T') & (~in_file.Client.isin(['ABC', 'DEF']))].sort_values('Value_01', ascending=False)
Out[29]:
  Client  Value_01  Value_02         Date
4    GHI        75        19  2016-09-01T
6    JKL        50         2  2016-09-01T

或者有点慢,但更好query()方法:

In [30]: in_file.query("Date == '2016-09-01T' and Client in ['ABC', 'DEF']")
Out[30]:
  Client  Value_01  Value_02         Date
0    ABC       100       500  2016-09-01T
2    DEF        95      1000  2016-09-01T

In [31]: in_file.query("Date == '2016-09-01T' and Client not in ['ABC', 'DEF']")
Out[31]:
  Client  Value_01  Value_02         Date
4    GHI        75        19  2016-09-01T
6    JKL        50         2  2016-09-01T

【讨论】:

    【解决方案2】:

    您的第二个子集数据框有两个相互冲突的条件

    (in_file.Client == 'ABC') & (in_file.Client == 'DEF')

    永远不可能同时为真。

    您似乎正在寻找的是“或”逻辑而不是“&”逻辑。所以

    df_02 = in_file.loc[(in_file.Date == '2016-09-02T') or (in_file.Client == 'ABC') or (in_file.Client == 'DEF')].sort_values('Value_01', ascending=False)

    会给你

    ABC     100       500       2016-09-01T
    ABC     14        90        2016-09-02T
    DEF     95        1000      2016-09-01T
    DEF     200       600       2016-09-02T
    GHI     300       700       2016-09-02T
    JKL     400       800       2016-09-02T
    

    【讨论】:

      【解决方案3】:

      警告这不是最好的解决方案!!!
      我只想指出你做错了什么。
      @MaxU 有最好的答案

      定义cond2

      cond2 = (in_file.Date == '2016-09-01T') & \
              (in_file.Client == 'ABC') & \
              (in_file.Client == 'DEF')
      

      这将永远是False,因为in_file.Client 永远不能同时是'ABC''DEF'。您必须使用“或”|

      相反

      cond2 = (in_file.Date == '2016-09-01T') & \
              ((in_file.Client == 'ABC') | (in_file.Client == 'DEF'))
      

      然后

      df_02 = in_file.loc[cond2].sort_values('Value_01', ascending=False)
      df_02
      


      但不要选择这个答案

      还不如用isin

      【讨论】:

        猜你喜欢
        • 1970-01-01
        • 1970-01-01
        • 2017-08-23
        • 2023-03-22
        • 1970-01-01
        • 2013-08-15
        • 1970-01-01
        • 2022-12-17
        • 2021-12-04
        相关资源
        最近更新 更多