获取最长单词长度的更pythonic方法是什么:
len(max(words, key=len))
或者:
max(len(w) for w in words)
或者是其他东西? words
是一个字符串列表。我发现我需要经常这样做,并且在使用几个不同的样本大小进行计时之后,第一种方法似乎始终更快,尽管在表面价值上似乎效率较低(len
被调用两次的冗余似乎无关紧要 - 在这种形式的C代码?)。
获取最长单词长度的更pythonic方法是什么:
len(max(words, key=len))
或者:
max(len(w) for w in words)
或者是其他东西? words
是一个字符串列表。我发现我需要经常这样做,并且在使用几个不同的样本大小进行计时之后,第一种方法似乎始终更快,尽管在表面价值上似乎效率较低(len
被调用两次的冗余似乎无关紧要 - 在这种形式的C代码?)。
虽然:
max(len(w) for w in words)
确实更容易“阅读” - 你有生成器的开销。
尽管:
len(max(words, key=len))
可以使用内置函数优化掉键,因为len
通常是一个非常有效的字符串操作,会更快......
我认为两者都可以,但我认为除非速度是max(len(w) for w in words)
最易读的一个重要考虑因素。
当我看着他们时,我花了更长的时间才弄清楚len(max(words, key=len))
在做什么,直到我想得更多,我还是错了。除非有充分的理由不这样做,否则代码应该立即显而易见。
从其他帖子(以及我自己的测试)中可以清楚地看出,可读性较低的帖子速度更快。但这并不像他们中的任何一个都是狗慢的。除非代码在关键路径上,否则不值得担心。
最终,我认为更具可读性的是 Pythonic。
顺便说一句,这是为数不多的 Python 2 在相同任务上明显快于 Python 3 的情况之一。
如果将生成器表达式重写为map
调用(或者,对于 2.x,imap
):
max(map(len, words))
…它实际上比关键版本快一点,而不是慢。
python.org 64 位 3.3.0:
In [186]: words = ['now', 'is', 'the', 'winter', 'of', 'our', 'partyhat'] * 100
In [188]: %timeit max(len(w) for w in words)
%10000 loops, best of 3: 90.1 us per loop
In [189]: %timeit len(max(words, key=len))
10000 loops, best of 3: 57.3 us per loop
In [190]: %timeit max(map(len, words))
10000 loops, best of 3: 53.4 us per loop
苹果 64 位 2.7.2:
In [298]: words = ['now', 'is', 'the', 'winter', 'of', 'our', 'partyhat'] * 100
In [299]: %timeit max(len(w) for w in words)
10000 loops, best of 3: 99 us per loop
In [300]: %timeit len(max(words, key=len))
10000 loops, best of 3: 64.1 us per loop
In [301]: %timeit max(map(len, words))
10000 loops, best of 3: 67 us per loop
In [303]: %timeit max(itertools.imap(len, words))
10000 loops, best of 3: 63.4 us per loop
我认为它比key
版本更 Pythonic,原因与 genexp 相同。
它是否与 genexp 版本一样 Pythonic 是有争议的。有些人爱map
/ filter
/ reduce
/等;有些人讨厌他们;我个人的感觉是,当您尝试映射一个已经存在并且具有好名字的函数时(也就是说,您不需要lambda
或partial
向上的东西),map
更好,但是 YMMV(特别是如果您的名字是 Guido) .
最后一点:
len 被调用两次的冗余似乎无关紧要 - 这种形式的 C 代码中会发生更多情况吗?
想一想:你已经调用了len
N 次。与您必须做的任何事情相比,将其称为N+1
时间几乎不可能有所作为N
,除非您有少量的大字符串。
我会说
len(max(x, key=len))
看起来相当不错,因为您使用内置 ( ) 的关键字参数 ( key
) 和max
内置 ( len
)。所以基本上max(x, key=len)
你几乎可以得到答案。但你的代码变体对我来说都不是特别不符合 Python 的。
仅供参考ipython %timeit
In [150]: words
Out[150]: ['now', 'is', 'the', 'winter', 'of', 'our', 'partyhat']
In [148]: %timeit max(len(w) for w in words)
100000 loops, best of 3: 1.87 us per loop
In [149]: %timeit len(max(words, key=len))
1000000 loops, best of 3: 1.35 us per loop
刚刚更新了更多的文字来展示@Omnifarious 的观点/评论。
In [160]: words = map(string.rstrip, open('/usr/share/dict/words').readlines())
In [161]: len(words)
Out[161]: 235886
In [162]: %timeit max(len(w) for w in words)
10 loops, best of 3: 44 ms per loop
In [163]: %timeit len(max(words, key=len))
10 loops, best of 3: 25 ms per loop
我知道现在已经一年了,但无论如何,我想出了这个:
'''编写一个函数find_longest_word(),它接受一个单词列表并返回最长单词的长度。'''
a = ['mamao', 'abacate', 'pera', 'goiaba', 'uva', 'abacaxi', 'laranja', 'maca']
def find_longest_word(a):
d = []
for c in a:
d.append(len(c))
e = max(d) #Try "min" :D
for b in a:
if len(b) == e:
print "Length is %i for %s" %(len(b), b)