Python 熊猫柱上的不等式

Python 熊猫柱上的不等式,python,pandas,dataframe,Python,Pandas,Dataframe,我有一个pandas数据框架,我想在现有列和某些不等式的基础上创建一个新列。例如,让 df=pd.DataFrame({'a':[1,2,3,4,5,6,7],'b':[3,6,4,2,7,7,1]}) 因此,df看起来像 a b 0 1 3 1 2 6 2 3 4 3 4 2 4 5 7 5 6 7 6 7 1 我想添加一个新列,res,如果a中的对应值小于2,则等于0;如果a中的对应值至少为2且小于4,则等于1;否则为2

我有一个pandas数据框架,我想在现有列和某些不等式的基础上创建一个新列。例如,让

df=pd.DataFrame({'a':[1,2,3,4,5,6,7],'b':[3,6,4,2,7,7,1]})
因此,
df
看起来像

    a   b
0   1   3
1   2   6
2   3   4
3   4   2
4   5   7
5   6   7
6   7   1
我想添加一个新列,
res
,如果
a
中的对应值小于2,则等于0;如果
a
中的对应值至少为2且小于4,则等于1;否则为2。所以我想

    a   b   res
0   1   3   0
1   2   6   1
2   3   4   1
3   4   2   2
4   5   7   2
5   6   7   2
6   7   1   2
到目前为止,我一直在使用
apply
进行以下操作:

def f(x):
    if x['a']<2:
        return 0
    elif x['a']>=2 and x['a']<4:
        return 1
    else:
        return 2
df['res']=df.apply(f,axis=1)
def(x):
如果x['a']=2且x['a']您可以使用:

输出:

   a  b res
0  1  3   0
1  2  6   1
2  3  4   1
3  4  2   2
4  5  7   2
5  6  7   2
6  7  1   2

对于一些值,也可以使用
numpy。其中
作为矢量化解决方案:

df['res'] = pd.np.where(df.a < 2, 0, pd.np.where((df.a >= 2) & (df.a < 4), 1, 2))
df
#   a   b   res
#0  1   3   0
#1  2   6   1
#2  3   4   1
#3  4   2   2
#4  5   7   2
#5  6   7   2
#6  7   1   2
df['res']=pd.np.where(df.a<2,0,pd.np.where((df.a>=2)和(df.a<4,1,2))
df
#a b res
#0  1   3   0
#1  2   6   1
#2  3   4   1
#3  4   2   2
#4  5   7   2
#5  6   7   2
#6  7   1   2

搜索排序

应该会给你带来更好的结果。与pd.cut类似,您需要指定断点

熊猫


numpy


定时

%timeit df.assign(res=pd.Series([2, 4]).searchsorted(df.a, side='right'))
%timeit df.assign(res=np.array([2, 4]).searchsorted(df.a.values, side='right'))
%timeit df.assign(res=pd.np.where(df.a < 2, 0, pd.np.where((df.a >= 2) & (df.a < 4), 1, 2)))
%timeit df.assign(res=pd.cut(df.a, [-np.inf,2,4,np.inf], labels=[0,1,2], right=False))

1000 loops, best of 3: 443 µs per loop
1000 loops, best of 3: 337 µs per loop
1000 loops, best of 3: 1.06 ms per loop
1000 loops, best of 3: 530 µs per loop
%timeit df.assign(res=pd.Series([2,4]).searchsorted(df.a,side='right'))
%timeit df.assign(res=np.array([2,4]).searchsorted(df.a.values,side='right'))
%timeit df.assign(res=pd.np.where(df.a<2,0,pd.np.where((df.a>=2)和(df.a<4,1,2)))
%timeit df.assign(res=pd.cut(df.a,[-np.inf,2,4,np.inf],labels=[0,1,2],right=False))
1000个回路,最佳3个:每个回路443µs
1000个回路,最好为3个:每个回路337µs
1000圈,最佳3圈:每圈1.06毫秒
1000个回路,最好为3个:每个回路530µs
df.assign(res=pd.Series([2, 4]).searchsorted(df.a, side='right'))

   a  b  res
0  1  3    0
1  2  6    1
2  3  4    1
3  4  2    2
4  5  7    2
5  6  7    2
6  7  1    2
df.assign(res=np.array([2, 4]).searchsorted(df.a.values, side='right'))

   a  b  res
0  1  3    0
1  2  6    1
2  3  4    1
3  4  2    2
4  5  7    2
5  6  7    2
6  7  1    2
%timeit df.assign(res=pd.Series([2, 4]).searchsorted(df.a, side='right'))
%timeit df.assign(res=np.array([2, 4]).searchsorted(df.a.values, side='right'))
%timeit df.assign(res=pd.np.where(df.a < 2, 0, pd.np.where((df.a >= 2) & (df.a < 4), 1, 2)))
%timeit df.assign(res=pd.cut(df.a, [-np.inf,2,4,np.inf], labels=[0,1,2], right=False))

1000 loops, best of 3: 443 µs per loop
1000 loops, best of 3: 337 µs per loop
1000 loops, best of 3: 1.06 ms per loop
1000 loops, best of 3: 530 µs per loop