从列表中删除所有特定类别的元素

3

我正在熟悉Python,目前正在学习基本的“列表”操作。

以下是我的问题:

我有一个包含大多数“字符串”类元素和两个整数的列表:

假设我只想删除整数类元素,以便我得到一个仅包含字符串元素的未更改列表:

即,我的原始列表如下:

    listoflists=[['Juice', 'Pizza', 'Potatoes', 'Bananas', 5, 10],
 ['eggs', 'ham', 'chicken', 'Pineapple'],
 'Onions']

我希望您能将以下内容转化为如下形式:

listoflist=[['Juice', 'Pizza', 'Potatoes', 'Bananas'],
 ['eggs', 'ham', 'chicken', 'Pineapple'],
 'Onions']

因此,我已经找到了从单个列表中删除整数类元素的方法,如下所示:

 no_integer_list = [x for x in listA if not isinstance(x, int)]

但我很难理解如何将其应用于列表的列表。

我考虑使用for循环来读取多重列表中的每个列表,并对每个列表应用上述代码,但我不确定如何做到这一点。

非常感谢您提供的任何帮助。


你的子列表有多深?只有1层吗? - luke14free
你的最后一个元素是有意为之的字符串吗? - miradulo
是的,我希望程序仅区分整数,并假设其他所有内容都可以保留,无论类型如何。 - Nathan
4个回答

4
假设您只有一个子列表级别(并且您的最后一个元素是一个列表而不是字符串),您可以使用嵌套列表推导式,如下所示。
filtered = [[x for x in sublist if not isinstance(x, int)] for sublist in listoflists]

输出:

[['Juice', 'Pizza', 'Potatoes', 'Bananas'], ['eggs', 'ham', 'chicken', 'Pineapple'], ['Onions']]

如果您的最后一个元素是字符串(或可能是int),我建议放弃混乱的一行代码并编写一个简单的函数,例如:

def filter_list(listoflists):
    newlist = []
    for element in listoflists:
        if isinstance(element, list):
            newlist.append([x for x in element if not isinstance(x, int)])
        elif isinstance(element, int):
            continue
        else:
            newlist.append(element)
    return newlist

请注意,这个设计只是为了删除所有的 int 类型 - 其他类型将保留。如果你想只保留字符串并且丢弃所有其他类型,你可以停用否定并使用以下代码:
def filter_list(listoflists):
    newlist = []
    for element in listoflists:
        if isinstance(element, list):
            newlist.append([x for x in element if isinstance(x, str)])
        elif isinstance(element, str):
            newlist.append(element)
    return newlist 

1
最后一个元素不是列表,而只是一个字符串。 - AKS
它仍然无法工作,请检查我在AKS答案下的评论。 - Mazdak
非常感谢@DonkeyKong,你似乎和我想的一样。 :-) - Nathan

1
>>> [[i for i in item if not isinstance(i, int)] if isinstance(item, list) else item for item in listoflists]
[['Juice', 'Pizza', 'Potatoes', 'Bananas'],
 ['eggs', 'ham', 'chicken', 'Pineapple'],
 'Onions']

更新: 仅为完整起见,如果您的外部列表也包含整数并且您也想将其删除:

[[i for i in item if not isinstance(i, int)] if isinstance(item, list) else item 
 for item in listoflists if not isinstance(item, int)]

1
这不适用于嵌套列表外的单个项目为整数的情况。 - Mazdak
但这不是我在问题中看到的用例?而且代码恰好得出了用户想要的结果。 - AKS
@Kasramvd,我编辑了答案,以捕捉该用例。 - AKS
就像你说的@AKS,它完成了我需要的工作。谢谢,非常感谢。正如Kasramvd所说,看到一些可以将嵌套列表之外的整数删除的代码会很有用。 - Nathan
@AKS,啊,非常感谢! :-) - Nathan

1
你的方法完全没问题,但你需要对每个子列表使用map()函数或列表推导式来完成。
>>> l = [['Juice', 'Pizza', 'Potatoes', 'Bananas', 5, 10], ['eggs', 'ham', 'chicken', 'Pineapple'], 'Onions']
>>> map(lambda x: filter(lambda y: not isinstance(y,int),x),l)
[['Juice', 'Pizza', 'Potatoes', 'Bananas'], ['eggs', 'ham', 'chicken', 'Pineapple'], 'Onions']

除了使用filter()和map(),您还可以使用等效的列表推导式方法。


0
一个灵活的递归解决方案,适用于任意数量的嵌套级别(甚至是不同深度)以及列表和元组(输出将为列表):
eliminate_int = lambda l: [eliminate_int(x) if isinstance(x, list) or isinstance(x, tuple) \
                           else x for x in l if not isinstance(x, int)]

listoflists=[ ['Juice', 'Pizza', 'Potatoes', 'Bananas', 5, 10],
              ['eggs', 'ham', 'chicken', 'Pineapple'],
              'Onions' ]

print(eliminate_int(listoflists))

输出:

[['Juice', 'Pizza', 'Potatoes', 'Bananas'], ['eggs', 'ham', 'chicken', 'Pineapple'], 'Onions']

在ideone.com上查看此代码运行情况


网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接