【问题标题】:How does one merge a list, but maintain the previous lists order?如何合并列表,但保持以前的列表顺序?
【发布时间】:2019-06-12 00:50:32
【问题描述】:

我有这个列表一旦合并使用下面给我这个输出。

['description t2_HELP', 'description t2_1507', 'description t2_1189', 'description t2_5625', 'description None', 'description None', 'description None', 'description None', 'interface Gi3/0/13', 'interface Gi3/0/7', 'interface Gi1/0/11', 'interface Gi3/0/41']

但是,当我合并数据时,我想保持该数据的顺序。所以示例列表集看起来像这样。

['interface Gi3/0/25','description None','description t2_2696','interface Gi1/0/29','description None','description t2_4148','interface Gi1/0/31','description None','description t2_4212','interface Gi2/0/31','description None','description t2_4271']

这是我合并列表的方式,

joinlist = data1 + data2 + data3

列表看起来像这样

data1 = ['interface Gi3/0/25','interface Gi1/0/29','interface Gi1/0/31','interface Gi2/0/31']
data2 = ['description None','description None','description None','description None']
data3 = ['description t2_2696','description t2_4148','description t2_4212','description t2_4271']

【问题讨论】:

  • 我们可以假设所有列表的大小始终相同吗?
  • @Paul 是对的。对于给定的输入列表,输出列表不正确
  • 也许可以使用更简单的例子,比如['a', 'b', ...]

标签: python list merge


【解决方案1】:

如果您有相同的长度 lists (zip) 或不介意结果中的填充值 (zip_longest),其他建议也可以。

但从逻辑上讲,您在这里要求的是循环输入,而不是压缩。通过展平,您会失去 zip 的配对方面,并且可能会因输入不均匀的长度而被它咬住。

the itertools module's roundrobin recipe 提供了针对此问题的更通用的解决方案(单击链接获取代码,我只是在此处包含用法):

joinlist = list(roundrobin(data1, data2, data3))

按顺序从每个输入中获取一个元素;如果一个输入比其他输入短,则在后面的轮次中将其省略,而不会注入垃圾填充值或丢失较长输入的值。

【讨论】:

    【解决方案2】:

    使用内置的zip 如果您可以接受任何更长的列表被截断:

    joinlist = []
    for d in zip(data1,data2,data3):
        joinlist.extend(d)
    

    输出:

    ['interface Gi3/0/25',
     'description None',
     'description t2_2696',
     'interface Gi1/0/29',
     'description None',
     'description t2_4148',
     'interface Gi1/0/31',
     'description None',
     'description t2_4212',
     'interface Gi2/0/31',
     'description None',
     'description t2_4271']
    

    如果您想避免截断,请使用itertools.zip_longest

    data2.append('test_me') # For testing purpose
    joinlist = []
    for d in zip_longest(data1,data2,data3):
        joinlist.extend(d)
    

    输出:

    ['interface Gi3/0/25',
     'description None',
     'description t2_2696',
     'interface Gi1/0/29',
     'description None',
     'description t2_4148',
     'interface Gi1/0/31',
     'description None',
     'description t2_4212',
     'interface Gi2/0/31',
     'description None',
     'description t2_4271',
     None,
     'a',
     None]
    

    注意:joinlist 末尾的None 是因为zip_longest 默认使用None 压缩更短的迭代。您可以使用zip_longest 中的fillvalue 设置任何默认值。

    【讨论】:

      【解决方案3】:

      您可以结合使用列表推导和zip

      >>> [i for t in zip(data1, data2, data3) for i in t]
      ['interface Gi3/0/25', 'description None', 'description t2_2696', 'interface Gi1/0/29', 'description None', 'description t2_4148', 'interface Gi1/0/31', 'description None', 'description t2_4212', 'interface Gi2/0/31', 'description None', 'description t2_4271']
      

      【讨论】:

      • 注意:itertools's chain.from_iterable 的存在是为了优化这样的用例(并启用一些 CPython zip 优化 list 理解不能使用):list(chain.from_iterable(zip(data1, data2, data3)))
      猜你喜欢
      • 1970-01-01
      • 2022-12-24
      • 2020-01-18
      • 1970-01-01
      • 2011-12-30
      • 2019-06-08
      • 2021-06-09
      • 2018-11-01
      • 2012-11-22
      相关资源
      最近更新 更多