将列表拆分为值上的嵌套列表
假设我有一个像这样的列表:
[1, 4, None, 6, 9, None, 3, 9, 4]
我决定将其拆分为 None
上的嵌套列表,以获得:
[[1, 4], [6, 9], [3, 9, 4]]
当然,我可能想在 (9, None)< 上执行此操作/code> 在这种情况下,我们会得到:
[[1, 4], [6], [3], [4]]
这对于通过迭代(在 for 循环中)使用列表追加来说是微不足道的
我有兴趣知道这是否可以更快地完成 - 比如列表理解?
如果没有,为什么不呢? (例如,列表推导式每次迭代不能返回多个列表元素?)
Say I have a list like so:
[1, 4, None, 6, 9, None, 3, 9, 4]
I decide to split this into nested lists on None
, to get this:
[[1, 4], [6, 9], [3, 9, 4]]
Of course, I could have wanted to do this on (9, None)
in which case, we would have got:
[[1, 4], [6], [3], [4]]
This is trivial to do using list append through iteration (in a for loop)
I am interested to know whether this can be done in something faster - like a list comprehension?
If not, why not? (for example, a list comprehension cannot return more than one list element per iteration?)
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(5)
基准代码:
i3-530、Windows7、Python 3.1.2 上的输出:
稍微修改了 Ryan 的代码,希望您不介意。
ssplit 是基于 Karl 的想法。添加了处理一些特殊情况的语句,使其成为 ssplit2,这是我可以提供的最佳解决方案。
benchmark code:
Output on i3-530, Windows7, Python 3.1.2:
Slightly modified Ryan's code, hope you don't mind.
ssplit was based on the idea of Karl. Added statements handling some special cases to became ssplit2 which is the best solution I may provide.
像这样的东西:
让我:
Something like this:
gets me:
您可以找到“分隔符”元素的索引。例如,None 的索引为 2 和 5(从零开始)。
您可以使用这些以及列表的长度来构造一个元组列表
[ (0,1), (3,4), (6,8) ]
表示起始索引和子列表的结束索引。然后,您可以对该元组列表使用列表理解来提取子列表。You could find the indices of the "delimiter" elements. For example, the indices of None are 2 and 5 (zero-based).
You could use these, along with the length of the list, to construct a list of tuples
[ (0,1), (3,4), (6,8) ]
representing the start indices and end indices of the sublists. Then you can use a list comprehension over this list of tuples to extract sublists.尝试使用列表理解的问题在于,理解本质上是无状态的,并且您需要状态来执行拆分操作。特别是,您需要记住,从一个元素到下一个元素,在前一个“分割”标记之后找到了哪些元素。
但是,您可以使用一种列表理解来提取拆分元素的索引,然后使用另一种列表理解来使用这些索引来分割列表。我们需要将分割索引转换为必要“片段”的(开始、结束)索引。我们要做的是将分割索引列表转换为两个单独的“开始”和“结束”列表,然后将它们压缩在一起。
整个事情看起来像:
The problem with trying to use a list comprehension for this is that the comprehension is inherently stateless, and you need state to perform the splitting operation. In particular, you need to remember, from one element to the next, what elements were found after the previous 'split' marker.
However, you could use one list comprehension to extract the indices of the split elements, and then another to use those indices to chop up the list. We need to translate the split indices into (begin, end) indices for the necessary 'pieces'. What we'll do is transform the list of split indices into two separate lists of 'begins' and 'ends', and then zip them together.
The whole thing looks like:
这是一个使用reduce 的实现,带有一些花哨的功能:
Here's an implementation using reduce, with a few bells and whistles: