Python:索引赋值中的for循环

2024-04-28 20:47:55 发布

您现在位置:Python中文网/ 问答频道 /正文

在阅读托比·塞加兰(Toby Segaran)的《编程集体智能》(Programming Collective Intelligence)一书时,我在索引作业中遇到了一些我并不完全熟悉的技巧。

以这个为例:

createkey='_'.join(sorted([str(wi) for wi in wordids]))

或:

normalizedscores = dict([(u,float(l)/maxscore) for (u,l) in linkscores.items()])

索引中的所有嵌套元组都让我有点困惑。这些变量的实际赋值是什么?我显然认为.join一个是字符串,但是后者呢?如果有人能解释这些环的机制,我将非常感激。我认为这些都是非常常见的技术,但是作为Python的新手,我想问一下是有点遗憾的。谢谢!


Tags: infor技巧智能编程作业collectiveprogramming
3条回答

后者相当于:

normalizedscores = {}
for u, l in linkscores.items():
    normalizedscores[u] = float(l) / maxscore
[str(wi) for wi in wordids]

是一个list comprehension

a = [str(wi) for wi in wordids]

a = []
for wi in wordids:
    a.append(str(wi))

所以

createkey='_'.join(sorted([str(wi) for wi in wordids]))

wordids中的每个项创建一个字符串列表,然后对该列表进行排序,并使用_作为分隔符将其连接到一个大字符串中。

正如agf所正确指出的,您还可以使用生成器表达式,它看起来就像一个列表理解,但是带有括号而不是括号。如果以后不需要列表,这可以避免构建列表(除了迭代它)。如果你已经有了括号,就像这里的sorted(...)一样,你可以简单地删除括号。

但是,在这种特殊情况下,您不会获得性能优势(实际上,它会慢10%左右;我对它进行了计时),因为sorted()无论如何都需要构建一个列表,但看起来更好一些:

createkey='_'.join(sorted(str(wi) for wi in wordids))

normalizedscores = dict([(u,float(l)/maxscore) for (u,l) in linkscores.items()])

遍历字典linkscores中的项,其中每个项都是键/值对。它创建一个键/l/maxscore元组列表,然后将该列表转换回字典。

但是,自从Python 2.7以来,您还可以使用dict comprehensions

normalizedscores = {u:float(l)/maxscore for (u,l) in linkscores.items()}

以下是一些计时数据:

Python 3.2.2版

>>> import timeit
>>> timeit.timeit(stmt="a = '_'.join(sorted([str(x) for x in n]))", setup="import random; n = [random.randint(0,1000) for i in range(100)]")
61.37724242267409
>>> timeit.timeit(stmt="a = '_'.join(sorted(str(x) for x in n))", setup="import random; n = [random.randint(0,1000) for i in range(100)]")
66.01814811313774

Python 2.7.2版

>>> import timeit
>>> timeit.timeit(stmt="a = '_'.join(sorted([str(x) for x in n]))", setup="import random; n = [random.randint(0,1000) for i in range(100)]")
58.01728623923137
>>> timeit.timeit(stmt="a = '_'.join(sorted(str(x) for x in n))", setup="import random; n = [random.randint(0,1000) for i in range(100)]")
60.58927580777687

我们来看看第一个:

  1. str(wi) for wi in wordids接受wordids中的每个元素并将其转换为字符串。
  2. sorted(...)对它们进行排序(按字典顺序)。
  3. '_'.join(...)将排序后的单词id合并为一个在条目之间带有下划线的字符串。

现在是第二个:

normalizedscores = dict([(u,float(1)/maxscore) for (u,l) in linkscores.items()])
  1. linkscores是字典(或类似字典的对象)。
  2. for (u,l) in linkscores.items()遍历字典中的所有条目,为每个条目分配键和值给ul
  3. (u,float(1)/maxscore)是一个元组,其第一个元素是u,第二个元素是1/maxscore(对我来说,这可能是一个拼写错误:float(l)/maxscore更合理——注意小写字母el代替一个)。
  4. dict(...)从元组列表中构造一个字典,其中每个元组的第一个元素作为键,第二个元素作为值。

简而言之,它复制字典,保留键并将每个值除以maxscore

相关问题 更多 >