Чтобы удалить завершающие нули, выполните:
result = df.groupby('proj').apply(
lambda grp: grp[grp.value[::-1].cumsum().gt(0)[::-1]])\
.reset_index(level=0, drop=True)
Лямбда-функция:
- принимает значение столбец в обратном порядке,
- вычисляет cumsum ,
- преобразуется в bool (is cumsum> 0),
- возвращается к «исходному» порядку,
- использует логическое индексирование для удаления конечных нулей.
Вышеупомянутая процедура повторяется для всех proj групп.
Все, что остается сделать (на этом step) равен reset_index , чтобы сбросить верхний уровень индекса (ключи группировки).
А теперь вторая часть - update weekduration :
result.weekduration = result.groupby('proj').weekduration\
.transform(lambda grp: grp.size)
Конечный результат:
proj weeknum weekduration value
0 1 1 2 0
1 1 2 2 11
4 2 1 3 10
5 2 2 3 11
6 2 3 3 12
Редактировать
Или, если вы предпочитаете решение «все в одном», определите следующую функцию для фильтрации группы и в то же время set weekduration :
def myFilter(grp):
grp = grp[grp.value[::-1].cumsum().gt(0)[::-1]]
grp.weekduration = grp.index.size
return grp
Затем вычислите результат, применив эту функцию к каждой группе (сгруппированной по proj ):
result = df.groupby('proj').apply(myFilter).reset_index(level=0, drop=True)