2012-03-15 22 views
19

Tengo una lista que tiene el número de marcas que los estudiantes tienen.Convertir números a grados en la lista de Python

s = [50,62,15,76,57,97,82,99,45,23] 

Quiero estudiantes de los grados de acuerdo a las marcas:

<40 - Fail 
>50 - A Grade 
>75 - A++ Grade 

puedo hacer esto con la iteración bucles o puedo encontrar todas las listas utilizando lambda. por ejemplo:

>>> filter(lambda x:x>=50, s) 
[50, 62, 76, 57, 97, 82, 99] 

Pero, en el filtro, puedo trabajar con una sola función a la vez (por ejemplo: marcas mayores de 50). ¿Hay alguna manera en que pueda usar filtro y lambda y obtener el resultado requerido en una línea? Esperando la salida como marcas con nota. (por ejemplo: 50 - A, 62 - A, 76 - A ++ ...)

Respuesta

21

definir una función que toma una marca y devuelve una representación legible por humanos, puede utilizar larsmans's expression o esta otra:

def grade(i): 
    if i<40: return "Fail" 
    if i>75: return "A++" 
    if i>50: return "A" 

uso string.format a formatee cada entrada y mapa para iterar sobre todos ellos:

li = map(lambda x: "{0} - {1}".format(x, grade(x)), s) 

La lista resultante ahora contiene cadenas en el formato deseado.

for i in li: print i 

# output 

50 - None 
62 - A 
15 - Fail 
76 - A++ 
57 - A 
97 - A++ 
82 - A++ 
99 - A++ 
45 - None 
23 - Fail 
+0

¿Cómo funciona {0} y {1 } ¿trabajo? – Josh

+0

@Josh http://docs.python.org/2/library/stdtypes.html#str.format – Anentropic

15

Olvídate de lambda, olvida filter; lo siguiente hace la calificación en una expresión, suponiendo que hay una calificación B entre A y "falla".

["fail" if g < 40 else "B" if g < 60 else "A" if g < 75 else "A++" for g in s] 

Puede zip el resultado de esto con s para obtener notas y calificaciones en una lista.

+0

o puede utilizar un mapa, 'mapa (lambda x: (x, ' F 'si x <40 else' A ++ 'si x> 70 else' A '), s) '. O simplemente pierda '(x,' (y ')' por supuesto) si solo quiere calificaciones. La lista está ordenada para que pueda coincidir más tarde. – rplnt

+0

Tu comprensión tiene 78 caracteres. Obtiene saltos de línea gratuitos en ellos. Sé que va en contra de las reglas de estilo de Google Python, pero prefiero romperlas en varias líneas, posiblemente al final de cada 'else'. – Droogans

+0

@Droogans: No conozco las reglas de estilo de Google, pero en un programa práctico, de hecho, pondría algunos saltos de línea. Http://stackoverflow.com/a/5809080/166749 –

1

Usted puede escribir su propio filtro como función:

def filter_n(n, f, lst): 
    result = tuple([[] for i in range(n)]) 
    for elem in lst: 
     result[f(elem)].append(elem) 
    return result 

La respuesta está buscando ahora de la siguiente manera:

grades = filter_n(3, lambda x: (x < 40) * 0 + 
           (60 < x <= 75) * 1 + 
           (75 < x) * 2, s) 
2
s = [50,62,15,76,57,97,82,99,45,23] 
x = dict([(a, 'A++' if a>75 else 'A' if a>55 else 'F') for a in s]) 

print x 

{97: 'A++', 45: 'F', 99: 'A++', 76: 'A++', 82: 'A++', 15: 'F', 50: 'F', 23: 'F', 57: 'A', 62: 'A'} 

Uso x.items() a hacer de filtro, por ejemplo

filter(lambda x: x[1] == 'A', x.items()) 

el resultado es

[(57, 'A'), (62, 'A')] 
+0

2 ámbitos en una línea donde el nombre 'x' es algo diferente. No muy diferente de otras respuestas, por lo tanto, si tuviera el privilegio de edición, una edición podría haber sido mejor que una respuesta. –

Cuestiones relacionadas