ursteiner
ursteiner

Reputation: 149

Count number of consecutive True in column, restart when False

I work with the following column in a pandas df:

A
True
True
True
False
True
True

I want to add column B that counts the number of consecutive "True" in A. I want to restart everytime a "False" comes up. Desired output:

A      B
True   1
True   2
True   3
False  0
True   1
True   2

Upvotes: 2

Views: 855

Answers (4)

mozway
mozway

Reputation: 261810

You can use a combination of groupby, cumsum, and cumcount

df['B'] = (df.groupby((df['A']&
                      ~df['A'].shift(1).fillna(False) # row is True and next is False
                     )
                     .cumsum() # make group id
                     )
             .cumcount().add(1) # make cumulated count
             *df['A'] # multiply by 0 where initially False, 1 otherwise
           )

output:

       A  B
0   True  1
1   True  2
2   True  3
3  False  0
4   True  1
5   True  2

Upvotes: 0

Shubham Sharma
Shubham Sharma

Reputation: 71687

Using cumsum identify the blocks of rows where the values in column A stays True, then group the column A on these blocks and calculate cumulative sum to assign ordinal numbers

df['B'] = df['A'].groupby((~df['A']).cumsum()).cumsum()

       A  B
0   True  1
1   True  2
2   True  3
3  False  0
4   True  1
5   True  2

Upvotes: 5

Vidya Ganesh
Vidya Ganesh

Reputation: 818

Here's an example

v=0
for i,val in enumerate(df['A']):
    if val =="True":
        df.loc[i,"C"]= v =v+1
    else:
        df.loc[i,"C"]=v=0
df.head()

This will give the desired output

    A        C
0   True     1
1   True     2
2   True     3
3   False    0
4   True     1

Upvotes: 1

sam
sam

Reputation: 1896

Using a simple & native approach

(For a small code sample it worked fine)

import pandas as pd

df = pd.DataFrame({'A': [True, False, True, True, True, False, True, True]})

class ToNums:
  counter = 0
  @staticmethod
  def convert(bool_val):
    if bool_val:
      ToNums.counter += 1
    else:
      ToNums.counter = 0
    return ToNums.counter

df['B'] = df.A.map(ToNums.convert)

df
     A      B
0   True    1
1   False   0
2   True    1
3   True    2
4   True    3
5   False   0
6   True    1
7   True    2

Upvotes: 1

Related Questions