Pandas — выделить n-е последующее равное значение в столбце

#python #pandas

#python #pandas

Вопрос:

Я пытаюсь выяснить, как выделить n-е последующее значение (и следующие) в фрейме данных Pandas, чтобы получить что-то вроде:

  Example 1: highlight 3rd subsequent equal value in Column A:

 Column A | Desired_output
 1        | 0
 1        | 0
 1        | 1
 1        | 1
 1        | 1
 1        | 1
 0        | 0
 0        | 0

 Example 2: highlight 5th subsequent equal value in Column A:

 Column A | Desired_output
 1        | 0
 1        | 0
 1        | 0
 1        | 0
 1        | 1
 1        | 1
 0        | 0
 0        | 0
  

Это должно работать не только тогда, когда столбец A равен 1, но и с нулями. Основная идея такова: если у меня недостаточно последующих равных значений, мой код не должен их учитывать.

Я думал использовать команду pd.rolling_sum с динамическим окном, но у меня проблемы с приложением, у вас есть какие-либо идеи о том, как действовать дальше? Спасибо

Ответ №1:

Учитывая ваш фрагмент кода:

 import pandas as pd
df = pd.DataFrame({'A': [1,1,1,1,1,1,0,0]})

# set n as the number of repetitions to highlight:
n=3 #or n=5
  

У вас есть два разных способа справиться с этим:

Частный случай

Это может решить вашу конкретную проблему (для этого требуется, чтобы ваш столбец состоял только из 1 и 0) и нуждается в numpy:

 import numpy as np

df['Desired Output']=np.where(df.rolling(n).sum()%n==0, True, False)
  

Общий случай

Это позволяет вам решать различные виды сравнений между строками (не только проверять равенство), например:

 comparison = True

for i in range(n):
    comparison amp;= df['A'] == df['A'].shift(i)

df['Desired Output'] = comparison
  

Результаты для обоих случаев

Для n = 3 у вас будет:

     A   Desired Output
0   1   False
1   1   False
2   1   True
3   1   True
4   1   True
5   1   True
6   0   False
7   0   False
  

И для n = 5 у вас будет:

     A   Desired Output
0   1   False
1   1   False
2   1   False
3   1   False
4   1   True
5   1   True
6   0   False
7   0   False
  

Формат:

Если вам нужен новый столбец с 1 и 0, используя подход к конкретному случаю, вы можете просто использовать 1 и 0 вместо True и False при создании столбца, например:

 # consider that in this scenario, a sequence of zeros it will be flagged with 1
df['Desired Output']=np.where(df.rolling(n).sum()%n==0, 1, 0)
  

Если вы решите использовать общий случай, просто включите astype(int) при создании столбца, например:

 df['Desired Output'] = comparison.astype(int)
  

Комментарии:

1. Выглядит аккуратно! Спасибо, Жоао!

2. Я обновил свой ответ, теперь он содержит решение с переходом, которое вы искали. Пожалуйста, проверьте, решает ли это вашу проблему.