出于某种原因,这不起作用:
示例数据:
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 ))
但没有运气!
获取frameindex
或stopiteration
类型错误。
是什么赋予了,我怎样才能完成这项工作?
答案 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]