我的数据已配对,以便成对出现行,id
名为a
和b
:
>>> df = pd.DataFrame([['1a', 'A', 5], ['1b', 'B', 10], ['2a', 'C', 20],['2b', 'D', 4]], columns=['id', 'name', 'count'])
>>> df
id name count
0 1a A 5
1 1b B 10
2 2a C 20
3 2b D 4
1a
和1b
是一对,2a
和2b
是另一对。我想创建一个新列rel_count
,其中值是行自己的count
除以其合作伙伴的count
:
id name count rel_count
0 1a A 5 0.5
1 1b B 10 2.0
2 2a C 20 5.0
3 2b D 4 0.2
在熊猫中这样做的最佳方式是什么?
答案 0 :(得分:1)
您可以通过ravel重塑为二维数组,翻转和平展:
df = pd.DataFrame([['1a', 'A', 5], ['1b', 'B', 10],
['2a', 'C', 20],['2b', 'D', 4],
['3a', 'C', 10],['3b', 'D', 5]],
columns=['id', 'name', 'count'])
print (df)
id name count
0 1a A 5
1 1b B 10
2 2a C 20
3 2b D 4
4 3a C 10
5 3b D 5
#if not sorting by pairs
#df = df.sort_values('id')
a = df['count'].values.reshape(-1, 2)[:, ::-1].ravel()
print (a)
[10 5 4 20 5 10]
如果可能以某种方式区分群组 - 像@Zero评论的第一个字母或提取第一个int
值:
g = df['id'].str.extract('(\d+)', expand=False)
a = df.groupby(g)['count'].transform(lambda x: x[::-1])
print (a)
0 10
1 5
2 4
3 20
4 5
5 10
Name: count, dtype: int64
print (g)
0 1
1 1
2 2
3 2
4 3
5 3
Name: id, dtype: object
df['rel_count'] = df['count'] / a
print (df)
id name count rel_count
0 1a A 5 0.5
1 1b B 10 2.0
2 2a C 20 5.0
3 2b D 4 0.2
4 3a C 10 2.0
5 3b D 5 0.5
答案 1 :(得分:0)
可能不是最佳方法,但你可以这样做:
for index, row in df.iterrows():
if index % 2 == 0:
df.ix[index, 'rel_count'] = float(df.ix[index, 'count']) / df.ix[index+1, 'count']
else:
df.ix[index, 'rel_count'] = float(df.ix[index, 'count']) / df.ix[index-1, 'count']
答案 2 :(得分:0)
您也可以试试这个。
df["g_id"] = df.id.str[0]
df_groupbed = df.set_index(["name", 'id', 'g_id']).groupby("g_id")["count"]
df_groupbed.nlargest(2)/df_groupbed.nsmallest(2).values
g_id name id g_id
1 B 1b 1 2.0
A 1a 1 0.5
2 C 2a 2 5.0
D 2b 2 0.2
Name: count, dtype: float64
首先,我们使用g_id
方法添加str
。然后,我们按g_id
我使用nlargest
和nsmallest
来反转每个组中的顺序。
答案 3 :(得分:0)
偶数和奇数,我的意思是数据帧中的行。需要.values
来避免串联不匹配索引的问题。
import pandas as pd
import numpy as np
df = pd.DataFrame([['1a', 'A', 5], ['1b', 'B', 10], ['2a', 'C', 20],['2b', 'D', 4]], columns=['id', 'name', 'count'])
df['rel_count'] = np.nan
even = df.loc[::2, 'count']
odd = df.loc[1::2, 'count']
df.loc[::2, 'rel_count'] = even / odd.values
df.loc[1::2, 'rel_count'] = odd / even.values