Python修改列表列表
Python Modify List of Lists
给定以下列表:
iters=[['EY11', 'EY12', 'EY13', 'EY14'],
['EY21', 'EY22', 'EY23', 'EY24'],
['PY11', 'PY12', 'PY13', 'PY14'],
['PY21', 'PY22', 'PY23', 'PY24']]
我想像这样修改此列表以转置值(因为缺少更好的描述):
iters=[['EY11', 'EY21', 'PY11', 'PY21'],
['EY12', 'EY22', 'PY12', 'PY22'],
['EY13', 'EY23', 'PY13', 'PY23'],
['EY14', 'EY24', 'PY14', 'PY24']]
我可以像这样一次处理一个子列表:
[i[0] for i in iters]
但现在我只需要知道如何遍历每个子列表并自动生成新的列表列表(另外,我无法预测我的实际数据中会有多少子列表,所以我想避免对 i[0].
中的当前子列表数量进行硬编码
提前致谢!
你的意思是这样的吗:
iters=[['EY11', 'EY12', 'EY13', 'EY14'],
['EY21', 'EY22', 'EY23', 'EY24'],
['PY11', 'PY12', 'PY13', 'PY14'],
['PY21', 'PY22', 'PY23', 'PY24']]
def iterating(iters):
if len(iters) > 0:
range_len = len(iters[0])
ret = []
for idx in range(0,range_len):
ret.append([i[idx] for i in iters])
return ret
return None
if __name__ == '__main__':
print iterating(iters)
将输出到:
[['EY11', 'EY21', 'PY11', 'PY21'], ['EY12', 'EY22', 'PY12', 'PY22'], ['EY13', 'EY23', 'PY13', 'PY23'], ['EY14', 'EY24', 'PY14', 'PY24']]
函数大小不固定,但 id 假定列表中的所有列表大小相同。
最简洁的解决方案是使用the zip
function加星解包:
newiters = list(zip(*iters)) # Wrapping in list not needed on Python 2
这几乎可以得到您想要的,但不完全是,因为它将是 tuple
中的 list
;如果没问题,你就完成了,如果没有,你只需调整它以转换为 list
s:
newiters = list(map(list, zip(*iters))) # Wrapping in list not needed on Python 2
这样做的原因是星号解包使得它就像你将 iters
的每个元素作为顺序位置参数传递给 zip
,例如:
zip(['EY11', 'EY12', 'EY13', 'EY14'],
['EY21', 'EY22', 'EY23', 'EY24'],
['PY11', 'PY12', 'PY13', 'PY14'],
['PY21', 'PY22', 'PY23', 'PY24'])
而 zip
的整个 schtick 正在从一组可迭代对象中的匹配偏移量中生成新的 tuple
s 值,因此第一个 tuple
是每个参数的第一个元素(('EY11', 'EY21', 'PY11', 'PY21')
),second是每个参数的第二个元素(('EY12', 'EY22', 'PY12', 'PY22')
),等等
注意:这假设所有子 list
的长度相同。如果不是,您将丢失数据,因为 zip
在最短的可迭代对象耗尽时停止。如果您愿意,可以使用 itertools.zip_longest
将较短的迭代器填充到最长的迭代器的长度。
这是使用列表推导的单行代码。
transp = [[i[x] for i in iters] for x in range(0,4)]
除了遍历索引外,基本上与您所做的相同。
#Output
['EY11', 'EY21', 'PY11', 'PY21']
['EY12', 'EY22', 'PY12', 'PY22']
['EY13', 'EY23', 'PY13', 'PY23']
['EY14', 'EY24', 'PY14', 'PY24']
如果这是您需要对数组执行的唯一复杂操作,那么其他解决方案之一可能是最好的。但是,如果您不介意引入 numpy,那么有一个名为 transpose
.
的内置例程
import numpy as np
iters_np = np.array(iters).transpose()
print(iters_np)
>>>[['EY11' 'EY21' 'PY11' 'PY21']
>>> ['EY12' 'EY22' 'PY12' 'PY22']
>>> ['EY13' 'EY23' 'PY13' 'PY23']
>>> ['EY14' 'EY24' 'PY14' 'PY24']]
给定以下列表:
iters=[['EY11', 'EY12', 'EY13', 'EY14'],
['EY21', 'EY22', 'EY23', 'EY24'],
['PY11', 'PY12', 'PY13', 'PY14'],
['PY21', 'PY22', 'PY23', 'PY24']]
我想像这样修改此列表以转置值(因为缺少更好的描述):
iters=[['EY11', 'EY21', 'PY11', 'PY21'],
['EY12', 'EY22', 'PY12', 'PY22'],
['EY13', 'EY23', 'PY13', 'PY23'],
['EY14', 'EY24', 'PY14', 'PY24']]
我可以像这样一次处理一个子列表:
[i[0] for i in iters]
但现在我只需要知道如何遍历每个子列表并自动生成新的列表列表(另外,我无法预测我的实际数据中会有多少子列表,所以我想避免对 i[0].
中的当前子列表数量进行硬编码提前致谢!
你的意思是这样的吗:
iters=[['EY11', 'EY12', 'EY13', 'EY14'],
['EY21', 'EY22', 'EY23', 'EY24'],
['PY11', 'PY12', 'PY13', 'PY14'],
['PY21', 'PY22', 'PY23', 'PY24']]
def iterating(iters):
if len(iters) > 0:
range_len = len(iters[0])
ret = []
for idx in range(0,range_len):
ret.append([i[idx] for i in iters])
return ret
return None
if __name__ == '__main__':
print iterating(iters)
将输出到:
[['EY11', 'EY21', 'PY11', 'PY21'], ['EY12', 'EY22', 'PY12', 'PY22'], ['EY13', 'EY23', 'PY13', 'PY23'], ['EY14', 'EY24', 'PY14', 'PY24']]
函数大小不固定,但 id 假定列表中的所有列表大小相同。
最简洁的解决方案是使用the zip
function加星解包:
newiters = list(zip(*iters)) # Wrapping in list not needed on Python 2
这几乎可以得到您想要的,但不完全是,因为它将是 tuple
中的 list
;如果没问题,你就完成了,如果没有,你只需调整它以转换为 list
s:
newiters = list(map(list, zip(*iters))) # Wrapping in list not needed on Python 2
这样做的原因是星号解包使得它就像你将 iters
的每个元素作为顺序位置参数传递给 zip
,例如:
zip(['EY11', 'EY12', 'EY13', 'EY14'],
['EY21', 'EY22', 'EY23', 'EY24'],
['PY11', 'PY12', 'PY13', 'PY14'],
['PY21', 'PY22', 'PY23', 'PY24'])
而 zip
的整个 schtick 正在从一组可迭代对象中的匹配偏移量中生成新的 tuple
s 值,因此第一个 tuple
是每个参数的第一个元素(('EY11', 'EY21', 'PY11', 'PY21')
),second是每个参数的第二个元素(('EY12', 'EY22', 'PY12', 'PY22')
),等等
注意:这假设所有子 list
的长度相同。如果不是,您将丢失数据,因为 zip
在最短的可迭代对象耗尽时停止。如果您愿意,可以使用 itertools.zip_longest
将较短的迭代器填充到最长的迭代器的长度。
这是使用列表推导的单行代码。
transp = [[i[x] for i in iters] for x in range(0,4)]
除了遍历索引外,基本上与您所做的相同。
#Output
['EY11', 'EY21', 'PY11', 'PY21']
['EY12', 'EY22', 'PY12', 'PY22']
['EY13', 'EY23', 'PY13', 'PY23']
['EY14', 'EY24', 'PY14', 'PY24']
如果这是您需要对数组执行的唯一复杂操作,那么其他解决方案之一可能是最好的。但是,如果您不介意引入 numpy,那么有一个名为 transpose
.
import numpy as np
iters_np = np.array(iters).transpose()
print(iters_np)
>>>[['EY11' 'EY21' 'PY11' 'PY21']
>>> ['EY12' 'EY22' 'PY12' 'PY22']
>>> ['EY13' 'EY23' 'PY13' 'PY23']
>>> ['EY14' 'EY24' 'PY14' 'PY24']]