有条件地从 Pandas DataFrame 中采样行
Sampling rows from Pandas DataFrame conditionally
我有一个 pandas DataFrame,其中某些人的人数过多。我想进行二次抽样,将每个观察的数量限制在某个最大数量。
现在我正在循环执行此操作并尝试从字典中构建一个 DataFrame。但是索引正在妨碍我,我希望有人可以指出一些更简单的解决方案。真实数据,有 ~20K 行、~4K 列和~400 人。谢谢。
示例数据。
df = pd.DataFrame({'name': ["Alice", "Alice", "Charles", "Charles", "Charles", "Kumar", "Kumar", "Kumar", "Kumar"],
'height': [124, 125, 169, 178, 177, 172, 173, 175, 174]})
df
height name
0 124 Alice
1 125 Alice
2 169 Charles
3 178 Charles
4 177 Charles
5 172 Kumar
6 173 Kumar
7 175 Kumar
8 174 Kumar
现在我的代码,对于这个例子,试图将每个人限制在 2 行。
sub_df = []
for name in pd.unique(df.name):
sub_df.append(df[df.name == name].sample(n=2, random_state=42).to_dict())
pd.DataFrame(sub_df)
我得到了什么。
height name
0 {1: 125, 0: 124} {1: 'Alice', 0: 'Alice'}
1 {2: 169, 3: 178} {2: 'Charles', 3: 'Charles'}
2 {6: 174, 8: 175} {6: 'Kumar', 8: 'Kumar'}
我想要的
height name
0 125 Alice
1 124 Alice
2 169 Charles
3 178 Charles
4 174 Kumar
5 175 Kumar
在 'name'
上执行 groupby
,然后使用 sample
:
# groupby and sample
df = df.groupby('name').apply(lambda grp: grp.sample(n=2))
# formatting
df = df.reset_index(drop=True)
结果输出:
height name
0 125 Alice
1 124 Alice
2 177 Charles
3 169 Charles
4 175 Kumar
5 173 Kumar
我有一个 pandas DataFrame,其中某些人的人数过多。我想进行二次抽样,将每个观察的数量限制在某个最大数量。
现在我正在循环执行此操作并尝试从字典中构建一个 DataFrame。但是索引正在妨碍我,我希望有人可以指出一些更简单的解决方案。真实数据,有 ~20K 行、~4K 列和~400 人。谢谢。
示例数据。
df = pd.DataFrame({'name': ["Alice", "Alice", "Charles", "Charles", "Charles", "Kumar", "Kumar", "Kumar", "Kumar"],
'height': [124, 125, 169, 178, 177, 172, 173, 175, 174]})
df
height name
0 124 Alice
1 125 Alice
2 169 Charles
3 178 Charles
4 177 Charles
5 172 Kumar
6 173 Kumar
7 175 Kumar
8 174 Kumar
现在我的代码,对于这个例子,试图将每个人限制在 2 行。
sub_df = []
for name in pd.unique(df.name):
sub_df.append(df[df.name == name].sample(n=2, random_state=42).to_dict())
pd.DataFrame(sub_df)
我得到了什么。
height name
0 {1: 125, 0: 124} {1: 'Alice', 0: 'Alice'}
1 {2: 169, 3: 178} {2: 'Charles', 3: 'Charles'}
2 {6: 174, 8: 175} {6: 'Kumar', 8: 'Kumar'}
我想要的
height name
0 125 Alice
1 124 Alice
2 169 Charles
3 178 Charles
4 174 Kumar
5 175 Kumar
在 'name'
上执行 groupby
,然后使用 sample
:
# groupby and sample
df = df.groupby('name').apply(lambda grp: grp.sample(n=2))
# formatting
df = df.reset_index(drop=True)
结果输出:
height name
0 125 Alice
1 124 Alice
2 177 Charles
3 169 Charles
4 175 Kumar
5 173 Kumar