简体   繁体   English

使用Python中的itertools imap对列表列表进行排序

[英]Sorting a list of lists with itertools imap in Python

I'm wondering what's happening when I execute this code and also if there is a better way to accomplish the same task. 我想知道执行此代码时发生了什么,以及是否有更好的方法来完成相同的任务。 Is a list of lists being made in memory to preform the sort, and then bar is assigned to be an iterator of foo.values()? 是否在内存中创建了一个列表列表以进行排序,然后将bar分配为foo.values()的迭代器? Or possibly foo.values() is sorted in the allotted dictionary memory space (seems unlikely)? 还是foo.values()在分配的字典内存空间中排序(似乎不太可能)?

Imagine the first value in the list, the integer, refers to a line number in a file. 想象一下列表中的第一个值(整数)是指文件中的行号。 I want to open the file and update only the lines referenced in the foo.values() lists with the rest of the data in the list (EG update line 1 with strings '123' and '097'). 我想打开文件并仅使用列表中的其余数据更新foo.values()列表中引用的行(例如,使用字符串'123'和'097'的EG更新行1)。

from itertools import imap

>>> foo = {'2134':[1, '123', '097'], '6543543':[3, '1'], '12315':[2, '454']}
>>> bar = imap([].sort(), foo.values())

Thanks~ 谢谢〜

First, you're passing [].sort() , which is just None , as the first argument to imap , meaning it's doing nothing at all. 首先,您要传递[].sort() (它只是None )作为imap的第一个参数,这意味着它什么也不做。 As the docs explain: "If function is set to None, then imap() returns the arguments as a tuple." 正如文档所解释的:“如果将函数设置为None,则imap()会将参数作为元组返回。”

To pass a callable to a higher-order function like imap , you have to pass the callable itself, not call it and pass the result. 要将可调用对象传递给像imap这样的高阶函数,您必须传递可调用对象本身,而不是调用它并传递结果。

Plus, you don't want [].sort here; 另外,您不需要[].sort that's a callable with no arguments that just sorts an empty list, which is useless. 那是一个没有参数的可调用对象,它只对一个空列表进行排序,这是没有用的。

You probably wanted list.sort , the unbound method, which is a callable with one argument that will sort whatever list it's given. 您可能想要list.sort (未绑定方法),该方法是可调用的,带有一个参数,它将对给出的任何列表进行排序。


So, if you did that, what would happen is that you'd creating an iterator that, if you iterated it, would generate a bunch of None values and, as a side effect, sort each list in foo.values() . 因此,如果您这样做了,那将是您创建一个迭代器,如果您对其进行迭代,则将生成一堆None值,并且作为副作用,对foo.values()每个列表进行排序。 No new lists would be created anywhere, because list.sort mutates the list in-place and returns None . 不会在任何地方创建新列表,因为list.sort列表并返回None

But since you don't ever iterate it anyway, it hardly matters what you put into imap ; 但是,由于您无论如何都不会对其进行迭代,因此您对imap进行的输入几乎没有关系; what it actually does is effectively nothing. 实际上它实际上没有执行任何操作。


Generally, abusing map / imap /comprehensions/etc. 通常,滥用map / imap / comprehensions / imap for side-effects of the expressions is a bad idea. 因为表达式的副作用是一个坏主意。 An iterator that generates useless values, but that you have to iterate anyway, is a recipe for confusion at best. 生成无用的值但仍然必须迭代的迭代器充其量是造成混乱的秘诀。

The simple thing to do here is to just use a loop: 这里要做的简单事情就是使用循环:

for value in foo.values():
    value.sort()

Or, instead of sorting in-place, generate new sorted values: 或者,而不是就地排序,而是生成新的排序值:

bar = imap(sorted, foo.values())

Now, as you iterate bar , each list will be sorted and given to you , so you can use it. 现在,当您迭代bar ,将对每个列表进行排序并提供给您 ,以便您可以使用它。 If you iterate this, it will generate a sorted list in memory for each list… but only one will ever be alive at a time (unless you explicitly stash them somewhere). 如果您遍历这个,它在内存中生成每个列表排序列表...但只有一个将永远活着,在一个时间(除非你明确地藏匿某处他们)。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM