【问题标题】:How to uniformly handle A LIST or A LIST OF LIST (multi-dimensional list)如何统一处理 A LIST 或 A LIST OF LIST(多维列表)
【发布时间】:2012-02-28 03:02:21
【问题描述】:

没有任何繁重的库如numpy,我想在我的代码中统一处理单个列表或多维列表。例如,函数 sum_up(list_or_matrix) 应该 为参数 [1, 2, 3] 返回 6,为 [[1, 2, 3], [1, 2, 0]] 返回 9。

我的问题是: 1. 我是否可以在不明确检测输入维度的情况下进行编码,例如通过 isinstance(arg[0], (tuple, list))?

2.如果我必须这样做,是否有任何优雅的方法来检测列表的维度(列表的列表......),例如递归?

【问题讨论】:

    标签: python


    【解决方案1】:

    作为many users suggested,您始终可以使用 dict 而不是 list 进行任意维度的集合。字典接受元组作为参数,因为它们是可散列的。因此,您可以轻松地填写您的收藏,例如

    >>> m = {}
    >>> m[1] = 1
    >>> m[1,2] = 12
    >>> m[1,2,"three",4.5] = 12345
    >>> sum(m.values()) #better use m.itervalues() in python 2.* 
    12358
    

    【讨论】:

    • 在这种情况下,有没有像numpy数组的形状一样直接告诉数据结构维度的方法?比如{0:1, 1:2}的dim应该是2,而{(0, 0): 1, {0,1}: 2, {1,0}: 1, {1,1} : 2} 应该是 (2, 2)
    • set( len(dim) for dim in m if isinstance(dim,tuple)) 将为您提供所有项目的可能形状集,具有元组键
    • 是的,实际使用套装可能有点矫枉过正?对于多维键控字典,我正在考虑使用 (dim + 1 for dim in max(data.keys())) 谢谢!
    【解决方案2】:

    你可以使用递归来解决这个问题,像这样:

    #!/usr/bin/env python
    
    def sum(seq_or_elem):
      if hasattr(seq_or_elem, '__iter__'):
        # We were passed a sequence so iterate over it, summing the elements.
        total = 0
        for i in seq_or_elem:
          total += sum(i)
        return total
      else:
        # We were passed an atomic element, the sum is identical to the passed value.
        return seq_or_elem
    

    测试:

    >>> print(sum([1, 2, [3, [4]], [], 5]))
    15
    

    【讨论】:

      【解决方案3】:

      好吧,如果您打算使用单个函数来总结您的列表,例如sum_up(list_or_matrix),我看不到任何方法。

      如果您有一个list of lists,我只会想象您需要遍历该列表以找出它是一维列表还是二维列表。无论如何循环有什么问题?

      def sum_up(matrix):
          2DMatrix = False
          for item in matrix:
              if type(item) == list:
                  2DMatrix = True
      
          if(2DMatrix):
              //sum 2d matrix
          else:
              //sum 1d matrix
      

      【讨论】:

        【解决方案4】:

        对矩阵求和的简单方法如下:

        def sum_up(matrix):
            if isinstance(matrix, (tuple, list)):
                return sum(matrix)
            else:
                return sum((sum(x) for x in matrix))
        

        'else' 分支使用list comprehension,这是一个强大而快速的工具。

        【讨论】:

          【解决方案5】:

          你可以递归求和,直到你有一个标量值:

          def flatten(x):
              if isinstance(x, list):
                  return sum(map(flatten, x))
              return x
          

          注意:您可以使用collections.Iterable(或其他基类)代替list,具体取决于您要展平的内容。

          【讨论】:

            猜你喜欢
            • 2012-09-18
            • 1970-01-01
            • 2012-12-22
            • 2021-02-28
            • 2021-07-06
            • 1970-01-01
            • 2011-02-03
            • 2019-10-23
            • 2023-03-12
            相关资源
            最近更新 更多