I have a list:
i = [[1,2,3,[]],[],[],[],[4,5,[],7]]
I want to remove all the empty list:
[[1,2,3],[4,5,7]]
How can I do this?
Here is my code:
res = [ele for ele in i if ele != []]
Use a recursive function to remove the empty list from a list.
Using recursion you can remove an empty list to any depth:
def remove_nested_list(listt):
for index, value in enumerate(reversed(listt)):
if isinstance(value, list) and value != []:
remove_nested_list(value)
elif isinstance(value, list) and len(value) == 0:
listt.remove(value)
a = [[1, 2, 3, 0, []], [], [], [], [4, 5, [], 7]]
print(f"before-->{a}")
remove_nested_list(a)
print(f"after-->{a}")
before-->[[1, 2, 3, 0, []], [], [], [], [4, 5, [], 7]]
after-->[[1, 2, 3, 0], [4, 5, 7]]
To remove empty lists from the arbitrarily nested list. We can use recursion here. Here's a simple way to do it. We need to iterate through the list and check if an element is an empty list. If yes, then we don't add it to the final list. If it's not an empty list we repeat the above process.
def remove_empty(lst):
return (
[remove_empty(i) for i in lst if i!=[]]
if isinstance(lst, list)
else lst
)
Output:
i = [[1, 2, 3, []], [], [], [], [4, 5, [], 7]]
print(remove_empty(i))
# [[1, 2, 3], [4, 5, 7]]
# Example taken from iGian's answer
ii = [[1, 2, 3, []], [], [], [], [4, 5, [], 7, [8, 9, [], [10, 11, []]]]]
print(remove_empty(ii))
# [[1, 2, 3], [4, 5, 7, [8, 9, [10, 11]]]]
To check if an object is iterable we use collection.abc.iterable
from collections.abc import Iterable
all(
isinstance(i, Iterable)
for i in ([], tuple(), set(), dict(), range(10), (_ for _ in range(10)))
)
# True
Now, you can replace isinstance(lst, list) with isinstance(lst, Iterable) to filter out empty list i.e [] from every iterable.
@Teepeemm pointed out a wonderful corner-case which all the answers missed.
To solve it we need two recursive functions one for checking if it's an empty nested list and the second one for remove empty nested lists
def empty(lst):
if lst == []:
return True
elif isinstance(lst, list):
return all(empty(i) for i in lst)
else:
return False
def remove_empty(lst):
return (
[remove_empty(i) for i in lst if not empty(i)]
if isinstance(lst, list)
else lst
)
i = [[1, 2, 3, [[]]]]
remove_empty(i)
# [[1, 2, 3]]
remove_nested_list(i) # Muhammad Safwan's answer
print(i) # [[1, 2, 3, []]]
ii = [[1, 2, 3, [[], [[[[], []]]]]]]
remove_empty(ii)
# [[1, 2, 3]]
remove_nested_list(ii) # Muhammad Safwan's answer
print(ii) # [[1, 2, 3, [[[[]]]]]]
I would use a couple of methods that doesn't mutate the original list.
The first simply removes all the empty lists in a list, not the nested:
def remove_empty_lists(lst):
return [ e for e in lst if not (isinstance(e, list) and len(e)==0) ]
The second method just uses the former in a recursive way:
def deep_remove_empty_lists(lst):
lst = remove_empty_lists(lst)
return [ deep_remove_empty_lists(e) if isinstance(e, list) else e for e in lst ]
So, in the submitted case:
i = [[1,2,3,[]],[],[],[],[4,5,[],7]]
deep_remove_empty_lists(i)
#=> [[1, 2, 3], [4, 5, 7]]
Or in a deepest nesting case:
ii = [[1,2,3,[]],[],[],[],[4,5,[],7,[8, 9, [], [10, 11, []]]]]
deep_remove_empty_lists(ii)
#=> [[1, 2, 3], [4, 5, 7, [8, 9, [10, 11]]]]