Python 按主题将列表分成若干部分

Python 按主题将列表分成若干部分,python,list,python-3.x,Python,List,Python 3.x,我有一份字典清单。可以假设每个列表都有相同格式的词典。让我们称之为格式: dict_sample={'a':0,'b':1} 我们还可以假设a是一个随机整数,而b可以是几个数字(或字符串)中的一个。我想按b对所有a值进行排序。例如,如果我有如下列表: a b 54 1 25 0 53 1 532 2 132 0 list=[{'a':54,'b':1},{'a':25,'b':0},{'a':53,'b':1},{'a':532,'b':2},{'a':132,'b':

我有一份字典清单。可以假设每个列表都有相同格式的词典。让我们称之为格式:

dict_sample={'a':0,'b':1}
我们还可以假设
a
是一个随机整数,而b可以是几个数字(或字符串)中的一个。我想按
b
对所有
a
值进行排序。例如,如果我有如下列表:

a    b
54   1
25   0
53   1
532  2
132  0

list=[{'a':54,'b':1},{'a':25,'b':0},{'a':53,'b':1},{'a':532,'b':2},{'a':132,'b':0}]
我想把它分为三个列表。清单包括(顺序不重要)

我知道我可以将列表中的所有
a
,如下所示,但我无法找到一个优雅的解决方案来将
a
b
排序。有什么建议吗?到目前为止,我的代码如下所示:

[row['a'] for row in list]
我想要的是这样的:

index=0      #This could be looped through, or just chosen for one specific value
[row['a'] if row['b']==index for row in list]
可行(且紧凑)的解决方案是:

output= { ok: [ ie['a'] for ie in list if ie['b'] == ok ] for ok in { e['b'] for e in list } }
注意,
{e['b']for e in list}
是一种集合理解(该语言相对较新的特性)。大致相当于
set([e['b']表示列表中的e])

我在CPython3.3.2上对它进行了测试,结果非常符合预期,除了在字典中。依我看,这些列表在字典中比在其他地方更有用,但为了符合这个问题:

list_0= output[0]
list_1= output[1]
list_2= output[2]
可行(且紧凑)的解决方案是:

output= { ok: [ ie['a'] for ie in list if ie['b'] == ok ] for ok in { e['b'] for e in list } }
注意,
{e['b']for e in list}
是一种集合理解(该语言相对较新的特性)。大致相当于
set([e['b']表示列表中的e])

我在CPython3.3.2上对它进行了测试,结果非常符合预期,除了在字典中。依我看,这些列表在字典中比在其他地方更有用,但为了符合这个问题:

list_0= output[0]
list_1= output[1]
list_2= output[2]
输出:

[(0, [25, 132]), (1, [54, 53]), (2, [532])]
输出:

[(0, [25, 132]), (1, [54, 53]), (2, [532])]

如果您已经知道所有的
b
值,那么这将是微不足道的。您需要每个
b
值的列表,其中每个值在每个字典中都有该
b
值的所有
a
值。你几乎可以直接从英语翻译成理解:

[[d['a'] for d in lst if d['b']==b] for b in bs]
您没有
b
值,但只需执行另一个过程即可获得它们:

bs = (d['b'] for d in lst)
除了您显然只需要唯一的值,并且您希望按排序顺序迭代它们,因此:

bs = sorted(set(d['b'] for d in lst))
这就是全部。综合起来:

>>> lst=[{'a':54,'b':1},{'a':25,'b':0},{'a':53,'b':1},{'a':532,'b':2},{'a':132,'b':0}]
>>> bs = sorted(set(d['b'] for d in lst))
>>> [[d['a'] for d in lst if d['b']==b] for b in bs]
[[25, 132], [54, 53], [532]]

如果您已经知道所有的
b
值,那么这将是微不足道的。您需要每个
b
值的列表,其中每个值在每个字典中都有该
b
值的所有
a
值。你几乎可以直接从英语翻译成理解:

[[d['a'] for d in lst if d['b']==b] for b in bs]
您没有
b
值,但只需执行另一个过程即可获得它们:

bs = (d['b'] for d in lst)
除了您显然只需要唯一的值,并且您希望按排序顺序迭代它们,因此:

bs = sorted(set(d['b'] for d in lst))
这就是全部。综合起来:

>>> lst=[{'a':54,'b':1},{'a':25,'b':0},{'a':53,'b':1},{'a':532,'b':2},{'a':132,'b':0}]
>>> bs = sorted(set(d['b'] for d in lst))
>>> [[d['a'] for d in lst if d['b']==b] for b in bs]
[[25, 132], [54, 53], [532]]


你为什么不使用
(a,b)
元组呢?我真正的字典要长一点,我不想记住它们的索引方案是什么。我宁愿给每个值一个名称。
(a,b)
s可能很有用,那么,您就不能循环浏览列表中的每个字典,并根据b的值添加到适当的子列表中吗?还是我在这里遗漏了什么?即,为b的每个值创建一个列表。循环浏览所有字典。如果(b==“type1”),则将
a
添加到type1列表中。等等。你为什么不使用
(a,b)
元组呢?我真正的字典要长一点,我不想记住它们的索引方案是什么。我宁愿给每个值一个名称。
(a,b)
s可能很有用,那么,您就不能循环浏览列表中的每个字典,并根据b的值添加到适当的子列表中吗?还是我在这里遗漏了什么?即,为b的每个值创建一个列表。循环浏览所有字典。如果(b==“type1”),则将
a
添加到type1列表中。等等。这比我的要好。这也很漂亮!这会给你一个(默认)dict而不是一个列表,这当然意味着它不是按排序顺序排列的……但是你可以总是用相应的键作为排序键,在一行中对dict的值进行排序。@abarnert:没有看到排序的要求-现在它也被排序了。这比我以前的排序方式要好得多。这也很巧妙!这将为您提供一个(默认)dict而不是一个列表,这当然意味着它不是按排序顺序排列的…但您始终可以使用相应的键作为排序键对dict的值进行排序,在另一行。@abarnert:没有看到排序的需求-现在它也被排序了。我所要做的就是把
if
放在
for
循环之后。唉。谢谢你指出我解决问题的错误@啊,我知道你哪里出错了。当你第一次看多句理解时,很多人认为它是由内而外的顺序最里面的表达在左边,所以它必须从右向左嵌套,对吗?但是不,最里面的表达式是特殊的,并且是首先出现的,但是子句是从左到右嵌套的。(这很难在评论中解释,但我怀疑你已经有了基本的想法,如果你需要细节,可以阅读参考文档,希望…)这肯定比它更有意义。我们必须继续尝试。谢谢@PearsonArtPhoto:如果你练习复杂理解和等效循环代码之间的映射(参考参考参考文档和/或尝试出错,如果你迷路了),在来回几次之后,它应该会突然在你的脑海中点击,从它们开始,多句理解是显而易见的(除了那些太长而无法在大脑中解析的语句……但英语也是如此,正如在英语中,你不应该写太长而无法在大脑中解析的语句,比如这个)。我所要做的就是把
if
放在
for
循环之后。叹气。谢谢你指出我解决问题的错误!@pearsonatphoto:啊,我明白了