2016-03-02 52 views
0

下面是代码如何在Python中使用递归来收集嵌套列表?

def list_all(obj): 
    """ 
    Return a list of all non-list elements in obj or obj's sublists, if obj is a list. Otherwise, return a list containing obj. 

    @param list|object obj: object to list 
    @rtype: list 

    >>> obj = 17 
    >>> list_all(obj) 
    [17] 
    >>> obj = [1, 2, 3, 4] 
    >>> list_all(obj) 
    [1, 2, 3, 4] 
    >>> obj = [[1, 2, [3, 4], 5], 6] 
    >>> all([x in list_all(obj) for x in [1, 2, 3, 4, 5, 6]]) 
    True 
    >>> all ([x in [1, 2, 3, 4, 5, 6] for x in list_all(obj)]) 
    True 
    """ 
    if not isinstance(obj, list): 
     return obj 
    else: 
     return [list_all(x) for x in obj] 

当我试图print(list_all([[2,3],[4,5]])),它打印出完全相同的输入,这意味着代码不会什么都没有。我认为问题是[]支架,但我想不出一种方法来消除。有人可以帮忙吗?

+5

我看不到你的代码不能正常工作,请再具体些! – Arman

+0

刚刚编辑,对此感到抱歉 – CoolKid

+0

你在做什么?压扁列表清单? – purpletentacle

回答

2

这应有助于:

def list_all(obj): 
    if not isinstance(obj, list): 
     return [obj] 
    else: 
     return [item for sublist in obj for item in list_all(sublist)]   

print(list_all(1))     # Scalar 
print(list_all([[2,3],[4,5]]))  # One level 
print(list_all([[2,[3,2]],[4,5]])) # Two levels 

输出:

[1] 
[2, 3, 4, 5] 
[2, 3, 2, 4, 5] 
+0

这会使一层嵌套变平,并且不处理顶层列表中包含一些标量值和一些子列表的情况。这对于[itertools'文档中的'flatten'配方](https://docs.python.org/3/library/itertools.html#itertools-recipes)并不是一个有意义的改进。唯一的区别是它不加修改地返回标量。 – ShadowRanger

+0

@ShadowRanger我不同意。该示例已经显示了两层嵌套。 – purpletentacle

+0

mtk99,我不明白downvote。对我来说看起来很好,我会投票决定你的解决方案。如果不对,人们应该在这里解释。 – danihp

0

像这样的事情,很抱歉没有测试过,但实在是微不足道....

def list_all(obj): 

    result= [] 
    if not isinstance(obj, list): 
     result.append(obj) 
    else: 
     for x in obj: 
      result += list_all(x) 
    return result 
1

而不是建造一帮中间的list s,请考虑使用生成器函数。特别是在Python 3.3+,代码很简单:

def flatten_lists(items): 
    if isinstance(items, list): 
     for x in items: 
      yield from flatten_lists(x) 
    else: 
     yield items 

如果需要的最终结果是一个list,你可以让来电者在list()包裹自己,或者你定义一个包装调用发电机和转换它的list他们:

def list_all(items): 
    return list(flatten_lists(items)) 

这大大降低了参与创建并与基于非发电解决方案的所有中间list S的处置分配器流失。

例子:

>>> list_all([1, [2, [3, [4, 5], 6]]]) 
[1, 2, 3, 4, 5, 6]