2012-05-10 14 views
38

Tengo una lista de números y quiero obtener el número de veces que aparece un número en una lista que cumple ciertos criterios. Puedo usar una lista de comprensión (o una lista de comprensión en una función) pero me pregunto si alguien tiene un camino más corto.número de valores en una lista mayor que un determinado número

# list of numbers 
j=[4,5,6,7,1,3,7,5] 
#list comprehension of values of j > 5 
x = [i for i in j if i>5] 
#value of x 
len(x) 

#or function version 
def length_of_list(list_of_numbers, number): 
    x = [i for i in list_of_numbers if j > number] 
    return len(x) 
length_of_list(j, 5) 

¿hay una versión aún más condensada?

Respuesta

80

Se podría hacer algo como esto:

>>> j = [4, 5, 6, 7, 1, 3, 7, 5] 
>>> sum(i > 5 for i in j) 
3 

En un principio puede parecer extraño para agregar True-True esta manera, pero no creo que es unpythonic; después de todo, boolis a subclass de int en todas las versiones desde 2.3:

>>> issubclass(bool, int) 
True 
+0

+1 Esta es una muy buena solución. – jamylak

+1

@jamylak, ¿por qué es esto mejor que Greg Hewgill? Si bien es interesante y correcto, parece mucho menos intuitivo y menos obvio para otra persona que lee el código. – TJD

+1

@TJD No dije que era mejor, pero me gusta más. – jamylak

7

si está utilizando otro modo numpy, le puede ahorrar unos cuantos golpes, pero yo no creo que se hace mucho más rápido/compacto que la respuesta de senderle.

import numpy as np 
j = np.array(j) 
sum(j > i) 
9

Se puede crear un resultado intermedio más pequeño como este:

>>> j = [4, 5, 6, 7, 1, 3, 7, 5] 
>>> len([1 for i in j if i > 5]) 
3 
+8

O 'suma (1 para i en j si i> 5)' por lo que no tiene que cargar la lista en la memoria. – jamylak

3

A (un poco) de manera diferente:

reduce(lambda acc, x: acc + (1 if x > 5 else 0), j, 0)

1

Si está utilizando NumPy (como en la respuesta de ludaavic), para matrices de gran tamaño, es probable que desee utilizar la función sum de NumPy en lugar de la sum incluida en Python para una aceleración significativa, por ejemplo, a> 1000x aumento de velocidad por 10 millones de conjuntos de elementos en mi portátil:

>>> import numpy as np 
>>> ten_million = 10 * 1000 * 1000 
>>> x, y = (np.random.randn(ten_million) for _ in range(2)) 
>>> %timeit sum(x > y) # time Python builtin sum function 
1 loops, best of 3: 24.3 s per loop 
>>> %timeit (x > y).sum() # wow, that was really slow! time NumPy sum method 
10 loops, best of 3: 18.7 ms per loop 
>>> %timeit np.sum(x > y) # time NumPy sum function 
10 loops, best of 3: 18.8 ms per loop 

(anterior utiliza %timeit "mágica" de IPython para medir el tiempo)

1

forma diferente de contar usando módulo de dividir en dos:

>>> from bisect import bisect 
>>> j = [4, 5, 6, 7, 1, 3, 7, 5] 
>>> j.sort() 
>>> b = 5 
>>> index = bisect(j,b) #Find that index value 
>>> print len(j)-index 
3 
Cuestiones relacionadas