我有一个传递两个值的函数,然后迭代这些值的范围。值可以按任何顺序传递,因此我需要找到哪一个是最低的。我有这样的函数:
def myFunc(x, y):
if x > y:
min_val, max_val = y, x
else:
min_val, max_val = x, y
for i in range(min_val, max_val):
...
但为了节省一些屏幕空间,我最终将其更改为:
def myFunc(x, y):
min_val, max_val = sorted([x, y])
for i in range(min_val, max_val):
...
这有多糟糕?还有一种更好的方式仍然是一条线吗?
答案 0 :(得分:16)
def myFunc(x, y):
min_val, max_val = min(x, y), max(x, y)
编辑。基准min-max
版基于简单的if
。由于函数调用开销,min-max
比简单2.5x
长if
;见http://gist.github.com/571049
答案 1 :(得分:5)
由于OP的问题是使用x
和y
作为参数(不是lo
和hi
)提出的,我会选择(速度和清晰度):
def myfunc(x, y):
lo, hi = (x, y) if x < y else (y, x)
>>> timeit.repeat("myfunc(10, 5)", "from __main__ import myfunc")
[1.2527812156004074, 1.185214249195269, 1.1886092749118689]
>>> timeit.repeat("foo(10, 5)", "from __main__ import foo")
[1.0397177348022524, 0.9580022495574667, 0.9673979369035806]
>>> timeit.repeat("f3(10, 5)", "from __main__ import f3")
[2.47303065772212, 2.4192818561823515, 2.4132735135754046]
答案 2 :(得分:4)
我喜欢sorted
一个。聪明但不太聪明。以下是其他一些选择。
def myFunc(min, max):
if min > max: min, max = max, min
def myFunc(x, y):
min, max = min(x, y), max(x, y)
def myFunc(x, y):
min, max = [f(x, y) for f in (min, max)]
我承认最后一个有点傻。
答案 3 :(得分:4)
除非你需要微观优化,否则我只是为了这个
def myFunc(x, y):
for i in range(*sorted((x, y))):
...
虽然
更快def myFunc(x, y):
for i in range(x,y) if x<y else range(y,x):
...
<强> minmax.py 强>
def f1(x, y):
for i in range(min(x, y), max(x, y)):
pass
def f2(x, y):
for i in range(*sorted((x, y))):
pass
def f3(x, y):
for i in range(x, y) if x<y else range(y, x):
pass
def f4(x, y):
if x>y:
x,y = y,x
for i in range(x, y):
pass
def f5(x, y):
mn,mx = ((x, y), (y, x))[x>y]
for i in range(x,y):
pass
基准(无论订单如何,f3都是最快的)
$ python -m timeit -s"import minmax as mm" "mm.f1(1,2)"
1000000 loops, best of 3: 1.93 usec per loop
$ python -m timeit -s"import minmax as mm" "mm.f2(1,2)"
100000 loops, best of 3: 2.4 usec per loop
$ python -m timeit -s"import minmax as mm" "mm.f3(1,2)"
1000000 loops, best of 3: 1.16 usec per loop
$ python -m timeit -s"import minmax as mm" "mm.f4(1,2)"
100000 loops, best of 3: 1.2 usec per loop
$ python -m timeit -s"import minmax as mm" "mm.f5(1,2)"
1000000 loops, best of 3: 1.58 usec per loop
$ python -m timeit -s"import minmax as mm" "mm.f1(2,1)"
100000 loops, best of 3: 1.88 usec per loop
$ python -m timeit -s"import minmax as mm" "mm.f2(2,1)"
100000 loops, best of 3: 2.39 usec per loop
$ python -m timeit -s"import minmax as mm" "mm.f3(2,1)"
1000000 loops, best of 3: 1.18 usec per loop
$ python -m timeit -s"import minmax as mm" "mm.f4(2,1)"
1000000 loops, best of 3: 1.25 usec per loop
$ python -m timeit -s"import minmax as mm" "mm.f5(2,1)"
1000000 loops, best of 3: 1.44 usec per loop
答案 4 :(得分:2)
一些建议
def myfunc(minVal, maxVal):
if minVal > maxVal: minVal, maxVal = maxVal, minVal
def myfunc2(a, b):
minVal, maxVal = ((a, b), (b, a))[a > b] # :-P
在这种情况下,使用sorted,min / max builtins或上面的第二个解决方案似乎有点过分了。
请记住range(min, max)
将从min
迭代到max - 1
!
答案 5 :(得分:2)
单个最佳答案的作用如下:
def foo(lo, hi):
if hi < lo: lo,hi = hi,lo
很明显,重点突出,并没有在一堆额外的胶水中掩盖意义。它很短。它几乎肯定与实践中的任何其他选项一样快,并且它依赖于最少的聪明。