Если, как в вашем примере, число строк в 'atm_id' кратно 3, то вы можете использовать iloc[::3]
для выбора каждых 3 строк.
# initiate the column
df['Period'] = None
# select every three rows and assign 1 there in the column Period
df['Period'].iloc[::3] = 1
# use cumsum, ffill and astype to populate an incremental value every 3 rows
df['Period'] = df['Period'].cumsum().ffill().astype(int)
Теперь я предполагаю, что вы не всегда будете иметь количество строк, кратное 3, в пределах atm_id
, поэтому вы можете перейти к groupby
и apply
. Я добавил строку к вашему вводу с atm_id = 2
, чтобы сделать точку. Если вы делаете:
print (df.groupby('atm_id').apply(lambda x: x.iloc[::3]))
atm_id dNDCSessionTime sCardNumber nTrRequestCount Period
atm_id
0 152865 0 2017-01-14 07:56:17 1 1 None
153054 0 2017-01-14 08:03:41 1 1 None
1 152806 1 2017-01-14 08:06:08 1 1 None
152866 1 2017-01-14 08:08:50 1 1 None
2 152887 2 2017-01-12 07:56:17 1 1 None
так что вы получите каждые 3 строки в пределах одного atm_id
. Здесь можно использовать различные решения для использования вышеуказанной информации в df
, моя задача состоит в том, чтобы идти по индексным номерам, предполагая, что они уникальны в ваших данных. Создайте mask
с оригинальным индексным номером и используйте его с той же идеей, что и выше.
mask_index = df.groupby('atm_id').apply(lambda x: x.iloc[::3]).index.get_level_values(1)
#if you do print (mask_index), you get
#Out[35]: Int64Index([152865, 153054, 152806, 152866, 152887], dtype='int64')
# initiate the column
df['Period'] = None
# select every three rows within a same atm_id and assign 1 there in the column Period
df.loc[mask_index, 'Period'] = 1
# use cumsum, ffill and astype to populate have an incremental value every 3 rows
df['Period'] = df['Period'].cumsum().ffill().astype(int)
результат похож на
atm_id dNDCSessionTime sCardNumber nTrRequestCount Period
152865 0 2017-01-14 07:56:17 1 1 1
153052 0 2017-01-14 08:01:13 1 1 1
153053 0 2017-01-14 08:02:19 1 1 1
153054 0 2017-01-14 08:03:41 1 1 2
152804 0 2017-01-14 08:04:37 1 1 2
152805 0 2017-01-14 08:05:24 1 1 2
152806 1 2017-01-14 08:06:08 1 1 3
152807 1 2017-01-14 08:07:15 1 1 3
152808 1 2017-01-14 08:08:08 1 1 3
152866 1 2017-01-14 08:08:50 1 1 4
152887 2 2017-01-12 07:56:17 1 1 5
, где вы можете увидеть приращение от 4 до 5 между двумя последними строками, в то время как для Period=4
нет 3 строк при изменении atm_id
Примечание: если ваши индексы не уникальны, то reset_index
в начале и set_index
в конце дают тот же результат, также я не sort_values
, как вы, но это не проблема.