如何在Pandas Dataframe中特定列值之后的n行之前或之后获取

时间:2019-01-09 08:27:57

标签: python pandas dataframe indexing

我有一个结果集,我想从中获得与特定单元格值匹配的行之后(之前)的下n行(或前n行)。

例如,这是我的数据:

A    B   C
1   10   2018-11-01
2   20   2018-10-31
3   30   2018-10-30
4   40   2018-10-29
5   50   2018-10-28
6   60   2018-10-27

我有兴趣在C = 2018-10-28(日期类型)的行之前获取3行,包括C = 2018-10-28的行,因此我的输出应为

 A    B   C
3   30   2018-10-30
4   40   2018-10-29
5   50   2018-10-28

我尝试了loc,但它需要索引,因此会引发错误:df2 = df2.loc[:C].tail(3)TypeError: can't compare datetime.date to int

3 个答案:

答案 0 :(得分:1)

  

我有兴趣在C = 2018-10-28的行之前获取3行

首先通过pd.Series.idxmax找到索引,然后使用pd.DataFrame.iloc进行切片,该方法支持整数位置索引:

idx = df['C'].eq('2018-10-28').idxmax()
res = df.iloc[idx-2: idx+1]

print(res)

#    A   B          C
# 2  3  30 2018-10-30
# 3  4  40 2018-10-29
# 4  5  50 2018-10-28

答案 1 :(得分:0)

您可以使用

s = StringIO("""
A    B   C
1   10   2018-11-01
2   20   2018-10-31
3   30   2018-10-30
4   40   2018-10-29
5   50   2018-10-28
6   60   2018-10-27""")

final = pd.read_csv(s, sep='\s\s+', engine='python')
final['C] = pd.to_datetime(final['C])

最终

  A   B           C
0  1  10  2018-11-01
1  2  20  2018-10-31
2  3  30  2018-10-30
3  4  40  2018-10-29
4  5  50  2018-10-28
5  6  60  2018-10-27

final.loc[final[final['C'] == '2018-10-28'].index[0]-2:final[final['C'] == '2018-10-28' ].index[0]]

输出

   A   B           C
2  3  30  2018-10-30
3  4  40  2018-10-29
4  5  50  2018-10-28

答案 2 :(得分:0)

检查dtypes中的df:如果df.dtypes列中的C不是日期时间,请将其转换为日期时间:

df.dtypes
Out[46]:
B     int64
C    object
dtype: object

df['C'] = pd.to_datetime(df['C'])
df.dtypes
Out[48]:
B             int64
C    datetime64[ns]
dtype: object

现在'C'列可与日期时间格式的字符串相提并论:

target_date = "2018-10-28"
df[df['C'] >= target_date].tail(3)
    B          C
A
3  30 2018-10-30
4  40 2018-10-29
5  50 2018-10-28

但是在更一般的情况下(目标列多于一个且数据是无序的),您可以使用以下方法:

df
A    B          C

0   10 2018-09-10
1   20 2018-07-11
2   20 2018-06-12
3   30 2018-07-13
4   50 2018-10-28
5   10 2018-11-01
6   20 2018-10-31
7   30 2018-10-30
8   40 2018-10-29
9   50 2018-10-28
10  60 2018-10-27

index = df[df['C'] == '2018-10-28'].index
index
Out:
Int64Index([4, 9], dtype='int64', name=0)

使用slice.iloc来获取目标:

slices = [slice(i, i-3, -1) for i in indicies]
slices
Out: [slice(4, 1, -1), slice(9, 6, -1)]

pd.concat([df.iloc[sl] for sl in slices])
    B          C
A
4  50 2018-10-28
3  30 2018-07-13
2  20 2018-06-12
9  50 2018-10-28
8  40 2018-10-29
7  30 2018-10-30

结果帧未排序,但很容易修复。这种方法仅适用于数字索引,但是在不存在的情况下,您可以仅使用pd.reset_index()进行添加。