'Pythonic way to a double comprehension

I have to get a list of handles and labels from a figure, except in the cases where the label is "True" or "False". The following code accomplishes this:

# h, l = [a for a in ax.get_legend_handles_labels()] #redundant
h, l = ax.get_legend_handles_labels()
handles = [a for a, b in zip(h, l) if (b != 'True' and b != 'False')]
labels = [b for a, b in zip(h, l) if (b != 'True' and b != 'False')]

Nevertheless, this seems completely "not-pythonic". Is there a more elegant way to solve this? I tried the following 2-liner but I got a ValueError: too many values to unpack (expected 2) on line 2:

h, l = [a for a in ax.get_legend_handles_labels()]
handles, labels = [(a,b) for a, b in zip(h, l) if (b != 'True' and b != 'False')]

I'd expect Python to have a one-line solution...is there any?

For reproducibility:

(h,l)=(['handle1','handle2', 'handle3'],['label1','True', 'False'])
handles = [a for a, b in zip(h, l) if (b != 'True' and b != 'False')]
labels = [b for a, b in zip(h, l) if (b != 'True' and b != 'False')]

The intended output for this reproducible example is

handles=['handle1'] 
labels=['label1']


Solution 1:[1]

There is a technique called "unzipping" an iterator (see fourth line in my code example), which is kind of a reshape of nested elements. It's a little bit like numpy's swapaxes if you are familiar with it. Combining python's iterators zip and filter you can achieve the desired behaviour in the following way:

h, l = ax.get_legend_handles_labels()
zipped = zip(h, l)
filtered = filter(lambda t: t[1] != 'True' and t[1] != 'False', zipped)
handles, labels = zip(*filtered)

Sources

This article follows the attribution requirements of Stack Overflow and is licensed under CC BY-SA 3.0.

Source: Stack Overflow

Solution Source
Solution 1 Alex G