[英]Shortest way to linearize a list in Python
I want to make a list with linearly increasing values from a list with non-linearly increasing values in Python. 我想从列表中使用线性增加的值创建一个列表,其中Python中的值非线性增加。 For example 例如
input =[10,10,10,6,6,4,1,1,1,10,10]
should be transformed to: 应转变为:
output=[0,0,0,1,1,2,3,3,3,0,0]
My code uses a python dictionary 我的代码使用python字典
def linearize(input):
"""
Remap a input list containing values in non linear-indices list
i.e.
input = [10,10,10,6,6,3,1,1]
output= [0,0,0,1,1,2,3,3]
"""
remap={}
i=0
output=[0]*len(input)
for x in input:
if x not in remap.keys():
remap[x]=i
i=i+1
for i in range(0,len(input)):
output[i]=remap[input[i]]
return output
but I know this code can be more efficient. 但我知道这段代码可以更有效率。 Some ideas to do this task better and in a more pythonic way, Numpy is an option? Numpy是一个选择,有些想法可以更好地以更加pythonic的方式完成这项任务吗? This function has to be called very frequently on big lists. 必须在大列表上频繁调用此函数。
As per your comment in the question , you are looking for something like this 根据你在问题中的评论 ,你正在寻找这样的东西
data = [8,8,6,6,3,8]
from itertools import count
from collections import defaultdict
counter = defaultdict(lambda x=count(): next(x))
print([counter[item] for item in data])
# [0, 0, 1, 1, 2, 0]
Thanks to poke , 感谢戳 ,
list(map(lambda i, c=defaultdict(lambda c=count(): next(c)): c[i], data))
Its just a one liner now :) 它现在只是一个班轮:)
Use collections.OrderedDict
: 使用collections.OrderedDict
:
In [802]: from collections import OrderedDict
...: odk=OrderedDict.fromkeys(l).keys()
...: odk={k:i for i, k in enumerate(odk)}
...: [odk[i] for i in l]
Out[802]: [0, 0, 0, 1, 1, 2, 3, 3, 3]
A simpler solution without imports: 没有导入的更简单的解决方案:
input =[10,10,10,6,6,4,1,1,1,10,10]
d = {}
result = [d.setdefault(x, len(d)) for x in input]
I came up with this function using numpy which in my tests worked faster than yours when input list was very big like 2,000,000 elements. 我想出了这个函数使用numpy,在我的测试中,当输入列表非常像2,000,000个元素时,它比你的更快。
import numpy as np
def linearize(input):
unique, inverse = np.unique(input, return_inverse=True)
output = (len(unique)-1) - inverse
return output
Also, this function only works if your input is in Descending order like your example. 此外,此功能仅在您的输入符合您的示例的降序时才有效 。 Let me know if it helps. 如果有帮助,请告诉我。
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.