Warning: file_get_contents(/data/phpspider/zhask/data//catemap/2/python/330.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Python 按列表元素在另一个列表上的成员顺序对列表元素进行分组_Python_List_Set - Fatal编程技术网

Python 按列表元素在另一个列表上的成员顺序对列表元素进行分组

Python 按列表元素在另一个列表上的成员顺序对列表元素进行分组,python,list,set,Python,List,Set,如果我有一个连续整数列表x(每个连续整数至少出现一次) 表示另一个列表的组成员身份,y y = [0, 0, 100, 30, 2000, 100, 1000, 40, 4] 提取所有分组列表的最干净的方法是什么,z?(注意:z中每个子列表中的顺序并不重要。) 我有一种直觉,我可以在一行中完成它,但我无法理解。您可以创建列表字典(使用defaultdict实现),然后用相应的值更新每个索引位置。这是使用zip将结果配对完成的 from collections import defaultdic

如果我有一个连续整数列表
x
(每个连续整数至少出现一次)

表示另一个列表的组成员身份,
y

y = [0, 0, 100, 30, 2000, 100, 1000, 40, 4]
提取所有分组列表的最干净的方法是什么,
z
?(注意:
z
中每个子列表中的顺序并不重要。)


我有一种直觉,我可以在一行中完成它,但我无法理解。

您可以创建列表字典(使用
defaultdict
实现),然后用相应的值更新每个索引位置。这是使用zip将结果配对完成的

from collections import defaultdict

dd = defaultdict(list)

for key, val in zip(x, y):
    dd[key].append(val)

>>> dd.values()
[[0, 0], [100, 100, 1000], [2000], [30], [40, 4]]
要确保输出匹配键的排序顺序,请执行以下操作:

>>> [dd[key] for key in sorted(dd.keys())]
[[0, 0], [100, 100, 1000], [2000], [30], [40, 4]]
计时

x = x * 10000
y = y * 10000

%%timeit
od = OrderedDict()
for k,v in zip(x, y):
    od.setdefault(k, []).append(v)
10 loops, best of 3: 49.7 ms per loop

%%timeit
dd = defaultdict(list)
for key, val in zip(x, y):
    dd[key].append(val)
100 loops, best of 3: 17.1 ms per loop

您可以创建列表字典(使用
defaultdict
实现),然后使用相应的值更新每个索引位置。这是使用zip将结果配对完成的

from collections import defaultdict

dd = defaultdict(list)

for key, val in zip(x, y):
    dd[key].append(val)

>>> dd.values()
[[0, 0], [100, 100, 1000], [2000], [30], [40, 4]]
要确保输出匹配键的排序顺序,请执行以下操作:

>>> [dd[key] for key in sorted(dd.keys())]
[[0, 0], [100, 100, 1000], [2000], [30], [40, 4]]
计时

x = x * 10000
y = y * 10000

%%timeit
od = OrderedDict()
for k,v in zip(x, y):
    od.setdefault(k, []).append(v)
10 loops, best of 3: 49.7 ms per loop

%%timeit
dd = defaultdict(list)
for key, val in zip(x, y):
    dd[key].append(val)
100 loops, best of 3: 17.1 ms per loop

您可以使用for循环保持顺序,使代码可读且高效:


除了导入和dict创建,创建配对需要两行代码,我认为这是非常合理的。

您可以保持顺序,使用for循环和:


除了导入和dict创建,我认为创建配对需要两行代码。

我喜欢
defaultdict
解决方案。为了摆脱未使用的列表理解,您可以将其与
reduce
配对:

from collections import defaultdict
z = reduce(lambda dct, kv: dct[kv[0]].append(kv[1]) or dct, zip(x,y), \     
           defaultdict(list))
这适用于Python2和Python3。 在Python2中,您可以使用参数unpacking(遗憾的是它在3中被删除):


这是您的一行解决方案-我将其拆分,但您不必:-)

我喜欢
defaultdict
解决方案。为了摆脱未使用的列表理解,您可以将其与
reduce
配对:

from collections import defaultdict
z = reduce(lambda dct, kv: dct[kv[0]].append(kv[1]) or dct, zip(x,y), \     
           defaultdict(list))
这适用于Python2和Python3。 在Python2中,您可以使用参数unpacking(遗憾的是它在3中被删除):


这是您的一行解决方案-我将其拆分,但您不必:-)

=
用于比较,
=
用于assignment@Padraic坎宁安我的错,这是一个打字错误。@jDo没错,我的第三行应该返回
True
@Katie
[[0,0]、[1001001000]、[2000]、[30]、[40,4]]
到底发生了什么?我们是说第一个数字分组吗?好的。那就忘了评论吧。
=
用于比较,
=
用于比较assignment@Padraic坎宁安,我的错,这是一个打字错误。@jDo没错,我的第三行应该返回
True
@Katie
[[0,0],[1001001000],[2000],[30],[40,4]]
到底是怎么回事?我们是说第一个数字分组吗?好的。那么,忘掉注释吧。
dd.values()
的顺序似乎是任意的。。。这就是OP想要的吗?是的,任意命令是可以的!谢谢很高兴添加计时
dd.values()
的顺序似乎是任意的。。。这就是OP想要的吗?是的,任意命令是可以的!谢谢很高兴添加计时