Панды подсчитывают количество значений, отличных от нуля между двумя нулями

1

У меня есть следующий датафрейм

0 0 0
1 0 0 
1 1 0
1 1 1
1 1 1
0 0 0
0 1 0
0 1 0
0 0 0 

как вы получаете датафрейм, который выглядит следующим образом

0 0 0
4 0 0 
4 3 0
4 3 2
4 3 2
0 0 0
0 2 0
0 2 0
0 0 0

Спасибо за помощь.

  • 1
    Какие отношения связывают эти две таблицы?
  • 1
    Нет описания и нет попытки.
Показать ещё 2 комментария
Теги:
pandas

2 ответа

1

Вам может понадобиться, используя цикл здесь, с tranform, и используя cumsum создать ключ и назначить позицию обратно к исходному ДФУ

for x in df.columns:
    df.loc[df[x]!=0,x]=df[x].groupby(df[x].eq(0).cumsum()[df[x]!=0]).transform('count')

df
Out[229]: 
     1    2    3
0  0.0  0.0  0.0
1  4.0  0.0  0.0
2  4.0  3.0  0.0
3  4.0  3.0  2.0
4  4.0  3.0  2.0
5  0.0  0.0  0.0
6  0.0  2.0  0.0
7  0.0  2.0  0.0
8  0.0  0.0  0.0

Или без циклы

s=df.stack().sort_index(level=1)
s2=s.groupby([s.index.get_level_values(1),s.eq(0).cumsum()]).transform('count').sub(1).unstack()
df=df.mask(df!=0).combine_first(s2)
df
Out[255]: 
     1    2    3
0  0.0  0.0  0.0
1  4.0  0.0  0.0
2  4.0  3.0  0.0
3  4.0  3.0  2.0
4  4.0  3.0  2.0
5  0.0  0.0  0.0
6  0.0  2.0  0.0
7  0.0  2.0  0.0
8  0.0  0.0  0.0
  • 0
    это так умно, молодец (еще раз)
  • 0
    @ Юка спасибо
0

Вот способ:

m = (df != df.shift(1)).cumsum()
df2 = pd.concat([df.iloc[:,i].groupby(m.iloc[:,i]).transform('size')
                for i in range(df.shape[1])], axis=1)

pd.DataFrame(np.where(df==1,df2, df))

   0  1  2
0  4  0  0
1  4  3  0
2  4  3  2
3  4  3  2
4  0  0  0
5  0  2  0
6  0  2  0
7  0  0  0

Куда:

(df != df.shift(1)).cumsum()
0  0.1  0.2
0  1    1    1
1  1    2    1
2  1    2    2
3  1    2    2
4  2    3    3
5  2    4    3
6  2    4    3
7  2    5    3

Который затем используется для группировки фрейма данных и получения size:

   0  0.1  0.2
0  4    1    2
1  4    3    2
2  4    3    2
3  4    3    2
4  4    1    4
5  4    2    4
6  4    2    4
7  4    1    4

Наконец, вы можете использовать np.where для замены тех значений, где df == 1:

pd.DataFrame(np.where(df==1,df2, df))

   0  1  2
0  4  0  0
1  4  3  0
2  4  3  2
3  4  3  2
4  0  0  0
5  0  2  0
6  0  2  0
7  0  0  0

Ещё вопросы

Сообщество Overcoder
Наверх
Меню