我已经写了这个简化的示例来说明我要实现的目标:
import pandas as pd
import pytest
def enable_rows(df, row, myrange):
# Need to modify this
df.loc[row + myrange:, 'enabled'] = True
df.loc[:row - myrange, 'enabled'] = True
def starting_df():
# just re-creates the initial dataframe to check on values
distance = {1: (100.0, 'a', False),
2: (100.0, 'a', False),
3: (100.0, 'a', False),
4: (700.0, 'b', False),
5: (700.0, 'b', False),
6: (900.0, 'c', False)}
return pd.DataFrame(data=list(distance.values()), index=list(
distance.keys()), columns=['distance', 'letter', 'enabled'])
def test_enable(center_row, myrange):
# convenience function to eye-candy the executions.
df = starting_df()
enable_rows(df, center_row, myrange)
print(df)
# assertions
enabled = df.loc[df.enabled]
if not ((len(enabled) == 3) and
(len(enabled.loc[df.distance == 100.0]) == 0) and
(len(enabled.loc[df.distance > 100.0]) == 3)):
print("wrong result")
test_enable(1, 2)
test_enable(2, 1)
距离数据帧具有几行具有相同的distance
和letter
列的或有行。最初它们都是enabled == False
我需要根据它们的enabled == True
索引和一个row
值来设置其中一些range
,以便所有与索引的行具有range
距离的行row
将被启用(而我设法加入了enable_rows
函数)。
另外,我需要如果一个distance
值未启用其所有行,则不应启用任何行。
两个示例中,某些distance == 100.0
行仍未启用,因此100.0都不应该启用。
他们期望结果数据帧为:
distance letter enabled
1 100.0 a False
2 100.0 a False
3 100.0 a False
4 700.0 b True
5 700.0 b True
6 900.0 c True
但是该程序的实际输出是:
distance letter enabled
1 100.0 a False
2 100.0 a False
3 100.0 a True
4 700.0 b True
5 700.0 b True
6 900.0 c True
wrong result
distance letter enabled
1 100.0 a True
2 100.0 a False
3 100.0 a True
4 700.0 b True
5 700.0 b True
6 900.0 c True
wrong result
我如何更新enable_rows
来获得它?
答案 0 :(得分:1)
如果所有groupby
的值都不是'distances'
,则只需transform
enabled
和True
的结果。您可以执行以下操作:
df['enabled'] = df.groupby('distance')['enabled'].transform(lambda x: all(x)==True)
您可以在这里使用
def enable_rows(df, row, myrange):
# Need to modify this
df.loc[row + myrange:, 'enabled'] = True
df.loc[:row - myrange, 'enabled'] = True
df['enabled'] = df.groupby('distance')['enabled'].transform(lambda x: all(x)==True)