eliminar el valor None de una lista sin eliminar el valor 0


Esta fue mi fuente con la que empecé.

Mi lista

L = [0, 23, 234, 89, None, 0, 35, 9]

Cuando corro esto:

L = filter(None, L)

Obtengo estos resultados

[23, 234, 89, 35, 9]

Pero esto no es lo que necesito, lo que realmente necesito es :

[0, 23, 234, 89, 0, 35, 9]

Porque estoy calculando el percentil de los datos y el 0 hacen mucha diferencia.

¿Cómo eliminar el valor None de una lista sin eliminar el valor 0?

Author: Matze, 2013-04-19

10 answers

>>> L = [0, 23, 234, 89, None, 0, 35, 9]
>>> [x for x in L if x is not None]
[0, 23, 234, 89, 0, 35, 9]

Solo por diversión, así es como puedes adaptarte filter para hacer esto sin usar un lambda, (no recomendaría este código, es solo para fines científicos)

>>> from operator import is_not
>>> from functools import partial
>>> L = [0, 23, 234, 89, None, 0, 35, 9]
>>> filter(partial(is_not, None), L)
[0, 23, 234, 89, 0, 35, 9]
 241
Author: jamylak,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2013-04-19 03:42:17

FWIW, Python 3 facilita este problema:

>>> L = [0, 23, 234, 89, None, 0, 35, 9]
>>> list(filter(None.__ne__, L))
[0, 23, 234, 89, 0, 35, 9]

En Python 2, usarías una comprensión de lista en su lugar:

>>> [x for x in L if x is not None]
[0, 23, 234, 89, 0, 35, 9]
 86
Author: Raymond Hettinger,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2013-04-19 04:16:12

Para Python 2.7 (Ver la respuesta de Raymond, para Python 3 equivalente):

Querer saber si algo "no es Ninguno" es tan común en python (y otros lenguajes OO), que en mi Common.py (que importo a cada módulo con " from Common import*"), incluyo estas líneas:

def exists(it):
    return (it is not None)

Luego, para eliminar Ninguno de los elementos de una lista, simplemente haga:

filter(exists, L)

Encuentro esto más fácil de leer, que la comprensión de la lista correspondiente (que Raymond muestra, como su versión de Python 2).

 15
Author: ToolmakerSteve,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2015-06-23 00:41:59

Usando la comprensión de lista esto se puede hacer de la siguiente manera:

l = [i for i in my_list if i is not None]

El valor de l es:

[0, 23, 234, 89, 0, 35, 9]
 10
Author: DotPi,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2018-02-17 14:25:32

@jamylak respuesta es bastante agradable, sin embargo, si no desea importar un par de módulos solo para hacer esta tarea simple, escriba su propio lambda en el lugar:

>>> L = [0, 23, 234, 89, None, 0, 35, 9]
>>> filter(lambda v: v is not None, L)
[0, 23, 234, 89, 0, 35, 9]
 8
Author: A T,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2017-08-20 00:41:50

Iteración vs Espacio, uso podría ser un problema. En diferentes situaciones, el perfilado puede mostrar que es" más rápido "y/o" menos memoria " intensiva.

# first
>>> L = [0, 23, 234, 89, None, 0, 35, 9, ...]
>>> [x for x in L if x is not None]
[0, 23, 234, 89, 0, 35, 9, ...]

# second
>>> L = [0, 23, 234, 89, None, 0, 35, 9]
>>> for i in range(L.count(None)): L.remove(None)
[0, 23, 234, 89, 0, 35, 9, ...]

El primer enfoque (como también sugirió @ jamylak, @Raymond Hettinger , y @Dipto) crea una lista duplicada en memoria, lo que podría ser costoso para una lista grande con pocas entradas None.

El segundo enfoque pasa por la lista una vez, y luego de nuevo cada vez hasta que se alcance un None. Esto podría ser menos intensivo en memoria, y la lista se hará más pequeña a medida que avanza. La disminución en el tamaño de la lista podría tener una velocidad para un montón de None entradas en el frente, pero el peor caso sería si un montón de None entradas estaban en la parte posterior.

La paralelización y las técnicas in situ son otros enfoques, pero cada uno tiene sus propias complicaciones en Python. Conocer los datos y los casos de uso de tiempo de ejecución, así como perfilar el programa son por dónde comenzar para operaciones intensivas o grandes datos.

Elegir cualquiera de los dos enfoques probablemente no importará en situaciones comunes. Se convierte más en una preferencia de notación. De hecho, en esas circunstancias poco comunes, numpy o cython pueden ser alternativas valiosas en lugar de intentar microgestionar optimizaciones de Python.

 4
Author: Kevin,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2018-02-19 16:51:38
from operator import is_not
from functools import partial   

filter_null = partial(filter, partial(is_not, None))

# A test case
L = [1, None, 2, None, 3]
L = list(filter_null(L))
 2
Author: med_abidi,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2016-11-23 08:29:58

Digamos que la lista es como la siguiente

iterator = [None, 1, 2, 0, '', None, False, {}, (), []]

Esto devolverá solo aquellos elementos cuya bool(item) is True

print filter(lambda item: item, iterator)
# [1, 2]

Esto es equivalente a

print [item for item in iterator if item]

Para filtrar ninguno:

print filter(lambda item: item is not None, iterator)
# [1, 2, 0, '', False, {}, (), []]

Equivalente a:

print [item for item in iterator if item is not None]

Para obtener todos los elementos que evalúan a False

print filter(lambda item: not item, iterator)
# Will print [None, '', 0, None, False, {}, (), []]
 1
Author: theBuzzyCoder,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2017-05-22 07:47:19

Si todo es una lista de listas, podría modificar la respuesta de sir @Raymond

L = [ [None], [123], [None], [151] ] no_none_val = list(filter(None.__ne__, [x[0] for x in L] ) ) para python 2 sin embargo

no_none_val = [x[0] for x in L if x[0] is not None] """ Both returns [123, 151]"""

>

 1
Author: screaminghard,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2017-09-10 13:54:50

Esta solución utiliza mientras en lugar de para:

value = None
while value in yourlist:
    yourlist.remove(value)
 -2
Author: Shupeng Xu,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2017-08-18 18:34:17