列表列表中的自定义切片
我有这个清单
MAIN = [
['ABC', '562', '112', '80', '231', '217', '433', '115', '10'],
['ABC', '562', '112', '80', '231', '322', '202', '432', '12'],
['ABC', '562', '112', '80', '231', '677', '133', '255', '64'],
['DEF', '711', '87', '319', '433', '981', '400', '100', '09'],
['DEF', '711', '87', '319', '433', '113', '210', '321', '51'],
['DEF', '711', '87', '319', '433', '921', '711', '991', '44']
]
我想从MAIN列表中生成 2 个列表。
1-首先获取A对于 MAIN 中的每个子列表,其元素从索引 0 到索引 4 的列表,结果是
A = [
['ABC', '562', '112', '80', '231'],
['ABC', '562', '112', '80', '231'],
['ABC', '562', '112', '80', '231'],
['DEF', '711', '87', '319', '433'],
['DEF', '711', '87', '319', '433'],
['DEF', '711', '87', '319', '433']
]
并删除重复项以最终获得此A列表:
A = [
['ABC', '562', '112', '80', '231'],
['DEF', '711', '87', '319', '433'],
]
2 -B为 中的每个子列表获取具有索引 0 和从索引 5 到索引 8 的元素的列表MAIN,结果是
B = [
['ABC', '217', '433', '115', '10'],
['ABC', '322', '202', '432', '12'],
['ABC', '677', '133', '255', '64'],
['DEF', '981', '400', '100', '09'],
['DEF', '113', '210', '321', '51'],
['DEF', '921', '711', '991', '44']
]
到目前为止,低于我的尝试:
获取列表 A
A = []
for z in MAIN:
y = z[:5]
if not (y in A):
A.append(y)
获取列表 B
B = []
for z in MAIN:
B.append(list(set(z) - set(z[1:5])))
在下面的结果中,列表似乎没问题A,但列表B的子列表顺序不同,最后一个子列表缺少元素。
A = [
['ABC', '562', '112', '80', '231'],
['DEF', '711', '87', '319', '433']
]
B = [
['217', '433', 'ABC', '10', '115'],
['322', '202', '432', 'ABC', '12'],
['255', '64', '677', 'ABC', '133'],
['09', '100', '400', '981', 'DEF'],
['113', '51', '210', '321', 'DEF'],
['DEF', '44', '991', '921']
]
将如何保证正确的输出的最佳方法A和B?谢谢你的帮助。
回答
您可以使用推导将切片应用于每个元素:
[x[:5] for x in MAIN]
我知道删除重复项的最佳方法是使用set. 但是,您无法向其中添加列表,因此您必须将切片包装在一个元组中:
A = list(set(tuple(x[:5]) for x in MAIN))
如果您希望元素是列表而不是元组,则必须显式转换它们:
A = list(map(list, set(tuple(x[:5]) for x in MAIN)))
您不能依赖于set为您创建切片,因为它不能保证顺序或保留重复项。相反,只需将切片附加在一起:
B = [x[:1] + x[5:9] for x in MAIN]
请注意,切片x[:1](又名x[0:1])创建了一个单元素列表,而x[0]将返回与标量相同的元素。任何索引n都可以通过n:n+1这种方式重写为切片。