[英]Changing Elif Statement to "Python-Like" Code
我明白 Python 就是关于效率的。 我将如何编写下面的代码以使其更加 Pythonic?
我想过使用字典,但由于elif
语句的条件是范围,我认为这是不可能的。
threshold_scale
if pop in range(threshold_scale[0], threshold_scale[1]):
color = '#ff0000'
elif pop in range(threshold_scale[1], threshold_scale[2]):
color = '#f6ff00'
elif pop in range(threshold_scale[2], threshold_scale[3]):
color = '#00ff08'
elif pop in range(threshold_scale[3], threshold_scale[4]):
color = '#0d00ff'
elif pop in range(threshold_scale[4], threshold_scale[5]+1):
color = '#ff00f7'
输出
[1960, 648065, 1294170, 1940275, 2586380, 3232486]
区间树是为这些类型的查询设计的。 一个例子是intervaltree
模块。
from intervaltree import IntervalTree, Interval
threshold_scale = [1960, 648065, 1294170, 1940275, 2586380, 3232486]
ranges = zip(threshold_scale, threshold_scale[1:])
colors = ["#ff0000", "#f6ff00", "$00ff08", "$0d00ff", "$ff00f7"]
t = IntervalTree([Interval(x, y, c) for (x,y), c in zip(ranges, colors)])
pop = 2000
color = sorted(t[2000])[0].data
对于n
区间,构建区间树需要O(n lg n)
时间,单个查询需要O(lg n)
时间。 (从技术上讲,它是O(lg n + m)
,其中m
是结果中的项目数。不过,我们的树由不重叠的范围组成,因此m
始终等于 1。)
相比之下,您的if
语句将花费O(n)
时间。 pop in range(...)
每次pop in range(...)
需要O(1)
时间,但可能有O(n)
个。 如果您需要针对同一组间隔进行多次查询,则使用间隔树会更快。
colors = [
'#ff0000',
'#f6ff00',
'#00ff08',
'#0d00ff',
'#ff00f7',
]
color = next(c for c, t_range in
zip(colors, zip(threshold_scale, threshold_scale[1:])) if
pop in range(*t_range))
给定输入:
threshold_scale = [0,2,4,6,8,10]
pop = 7
输出:
f6ff00
您可以使用numpy.digitize
import numpy as np
threshold_scale = [1960, 648065, 1294170, 1940275, 2586380, 3232486]
pop = [2000, 2000000, 2800000]
color = np.array(['#ff0000', '#f6ff00', '#00ff08', '#0d00ff', '#ff00f7'])
color[np.digitize(pop, threshold_scale) - 1]
您也将不得不处理覆盖范围之外的流行值......
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.