pythonnumpysignalssignal-processingphase

Most pythonic way of finding the "phase" (percentage of "completion", or relative position in a chunk) of a binary vector


Let's say I have a binary vector representing two phases:

signal = np.array([0, 0, 0, 0, 1, 1, 1, 0, 0, 1, 1, 1, 1])

I would like to compute, for each value of this vector, its "position" relative to its chunk, expressed, for instance, in percentage such as follows:

desired output:

[0, 0.33, 0.66, 0.99, 
 0, 0.5, 1, 
 0, 1, 
 0, 0.33, 0.66, 0.99]

I wonder what is the most efficient or pythonic way of obtaining that. One way would be to loop back and forth and compute the length of each "phase", and to divide the index accordingly, but that seems quite convoluted?

Thanks a lot :)


Solution

  • There's nothing un-Pythonic about writing loops, but if you absolutely must do everything with comprehensions and itertools, here's one way:

    import numpy as np
    from itertools import chain, groupby
    
    signal = np.array([0, 0, 0, 0, 1, 1, 1, 0, 0, 1, 1, 1, 1])
    
    result = list(chain.from_iterable(
        np.linspace(0, 1, sum(1 for _ in v))
        for _, v in groupby(signal)
    ))
    

    Result (do your own rounding if really necessary):

    [0.0, 0.3333333333333333, 0.6666666666666666, 1.0,
     0.0, 0.5, 1.0,
     0.0, 1.0,
     0.0, 0.3333333333333333, 0.6666666666666666, 1.0]
    

    Explanation: