pandas multi-group apply()更改视图值

时间:2014-07-10 23:22:59

标签: python pandas

出于某种原因,这不起作用:

示例数据:

dt = pd.DataFrame({'sid':['a']*9 + ['b']*9 + ['c']*9,
                   'src': [1] *18 + [2] * 9,
                   'val':np.random.randn(27),
                    'dval': [0]*18 + np.random.rand(9)})

我希望根据某些dval条件对src,sid进行多组分组并更改{c}行的val行值。

我一直收到StopIteration错误。

# -- set bycp threshold for probability val to alert
    def quantg(g):
        try:

            g['dval'] = g['dval'].apply(lambda x: x > x['val'].quantile(.90) and 1 or 0 )
            print '***** bycp ', g.head(2)
            #print 'discretize bycp ', g.head()
            return g
        except (Exception,StopIteration) as e:
            print '**bycp error\n', e
            print g.info()
            pass

然后我尝试在groupby之前按行过滤:

d = d[d['alert_t']=='bycp'].groupby(['source','subject_id','alert_t','variable']).apply(quantg )

我也尝试过mulitlevel选择:

 # -- xs for multilevel select
 g['dval'] = g.xs(('c','sid')).map(lambda x: len(g['value']) and\
                                                             #(x>g['value'].quantile(.90) and 1 or 0 ))

但没有运气!

获取frameindexstopiteration类型错误。

是什么赋予了,我怎样才能完成这项工作?

1 个答案:

答案 0 :(得分:2)

以下内容并不符合您的想法:

x > x['val'].quantile(.90) and 1 or 0

事实上,如果你尝试使用Series,它应该引发一个ValueError。

In [11]: dt and True
ValueError: The truth value of a DataFrame is ambiguous. Use a.empty, a.bool(), a.item(), a.any() or a.all().

在编写类似内容时,您要使用np.where

np.where(x > x['val'].quantile(.90), 1, 0)

注意:astype('int64')也可以使用,或者只是将其作为bool ...

但是,我想我可能会在这里使用转换(提取每个组的分位数,然后屏蔽掉它),例如:

q90 = g.transform(lambda x: x.quantile(.90))
df[df.val > q90]