I have a collection of lists of integer values in python like the following:
[0, 0, 1, 0, 1, 0, 0, 2, 1, 1, 1, 2, 1]
Now I would like to have a somewhat "smoothed" sequence where each value with the same preceding and following value (which both differ from the central value in question) is replaced with this preceeding-following value. So my list above becomes:
[0, 0, 0, 0, 0, 0, 0, 2, 1, 1, 1, 1, 1]
(The order or procession is from left to right, just to reconcile possible conflicting groupings.)
How could I achieve list?
Bonus: same as above with possible parametrization how many preceeding-following values must occur to change the central value (2-2 or 3-3 instead of just 1-1).
CodePudding user response:
arr = [0, 0, 1, 0, 1, 0, 0, 2, 1, 1, 1, 2, 1]
res = [arr[0]]
i = 0
for i in range(1,len(arr)):
if res[i-1] not in arr[i:i 2]:
res.append(arr[i])
else:
res.append(res[i-1] )
print(res)
CodePudding user response:
A straightforward loop should do the trick:
_list = [0, 0, 1, 0, 1, 0, 0, 2, 1, 1, 1, 2, 1]
for i in range(1, len(_list)-1):
if _list[i-1] == _list[i 1]:
_list[i] = _list[i-1]
print(_list)
Output:
[0, 0, 0, 0, 0, 0, 0, 2, 1, 1, 1, 1, 1]
CodePudding user response:
To allow the number of preceding / following values to be changed, you can create a 'pad' the list and iterate through a moving window on the padded list to check if all surrounding values are the same.
def smooth(lst, values=1, padding=None):
padded = [padding] * values lst [padding] * values
for i, n in enumerate(lst):
surrounding = set(padded[i:i values] padded[i values 1:i values*2 1])
if len(surrounding) == 1:
yield surrounding.pop()
else:
yield n
print(list(smooth([0, 0, 1, 0, 1, 0, 0, 2, 1, 1, 1, 2, 1]))) # [0, 0, 0, 1, 0, 0, 0, 2, 1, 1, 1, 1, 1]
If your input list may contain None
, choose a different padding parameter when calling the generator.