【问题标题】:Duplicating rows conditionally / Transform with function that conditionally returns rows有条件地复制行/使用有条件地返回行的函数进行转换
【发布时间】:2018-01-11 08:01:56
【问题描述】:

我想通过将列 'one' 扩展到索引为 'Derby' 的所有行来创建一个新列 'derby_one',如下面的 valid_result 所示

number              one  two  three
country town
AU      Newcastle     0    1      2
        Derby         3    4      5
        Sydney        6    7      8
UK      Derby         9   10     11
        Kensington   12   13     14
        Newcastle    15   16     17
USA     Derby        18   19     20

transform 函数可以实现类似的结果

data.groupby(['country']).one.transform(max)

但是,我不确定如何修改它以与索引器交互

示例数据

import pandas as pd
import numpy as np
data = pd.DataFrame(np.arange(21).reshape(7,3), index=pd.MultiIndex(levels=[[u'AU', u'UK', 'USA'], [u'Derby', u'Kensington', u'Newcastle', u'Sydney']], labels=[[0, 0, 0, 1, 1, 1, 2], [2, 0, 3, 0, 1, 2, 0]], names=[u'country', u'town']), columns=pd.Index(['one', 'two', 'three'], name='number'))

# create test data set
test = data.copy()
derby_one = pd.Series(np.array([0,0,0,9,9,9,18]), index=data.index)
test['derby_one'] = derby_one

注意事项

我不想使用连接/合并功能,因为我的真实数据集非常大,例如以下选项不可行

derby_one = data.loc[pd.IndexSlice[:, 'Derby'], ['one']].reset_index()
derby_one = derby_one[['country', 'one']].rename(columns={'one':'derby_one'})
pd.merge(
    data.reset_index(),
    derby_one,
    left_on=['country'],
    right_on=['country']).set_index(['country', 'town']
)

【问题讨论】:

  • 一个(现已删除)答案提供了一个带有.query('town == "Derby"') 的方法,然后使用ffill 填充np.nan 值。但是,这取决于位置,并且在数据未排序时会失败。 1)我怀疑ffill().bfill() 的组合可能会起作用。 2) .loc[pd.IndexSlice[:, 'Derby']]query 的两倍,结果相同

标签: python-2.7 pandas apply pandas-groupby


【解决方案1】:

您可以这样做,让 Pandas 为您对齐索引并使用 query 仅过滤那些“Derby”行,然后使用 groupbytransform 以分组填充 NaN 值:

data['derby_one'] = data.query('town == "Derby"')['one']
data.groupby(['country'])['derby_one'].transform(max)

输出

number              one  two  three  derby_one
country town                                  
AU      Derby         0    1      2        0.0
        Newcastle     3    4      5        0.0
        Sydney        6    7      8        0.0
UK      Derby         9   10     11        9.0
        Kensington   12   13     14        9.0
        Newcastle    15   16     17        9.0
USA     Derby        18   19     20       18.0

【讨论】:

  • 嗨,斯科特,如果您在不依赖 'Derby' 位于列表顶部但您的方法失败的情况下运行相同的答案,我已经进行了编辑以避免与位置相关的答案
  • @AlexanderMcFarlane 好的。我会修改的。
  • @AlexanderMcFarlane 好的,试试这个。
  • 哈,我以为你已经付出了所有努力,只是将其全部删除,所以我将其全部写在评论中:)
  • 是的,你需要在组中保留填充,所以除非它在该组的第一个或最后一个位置,我认为你将不得不 groupby。
猜你喜欢
  • 2021-04-08
  • 2018-08-17
  • 2023-03-07
  • 2013-02-03
  • 1970-01-01
  • 2013-05-15
  • 2022-12-03
  • 2020-03-20
  • 1970-01-01
相关资源
最近更新 更多