Hoy tenemos otro intento de meter lo imposible en una sola línea, encontrado en los rincones de internet. Al ver esto, los linters no solo se quejan, sino que se desinstalan de tu dispositivo.
with open("t") as f:print(sum([sum([float(m) for m in "".join(filter(lambda x:x.isnumeric() or x.isspace() or x==".",l)).split()]) for l in f.readlines()]))🧐 ¿Qué está pasando aquí?
El autor de esta «obra maestra» se propuso una tarea: extraer todos los números de un archivo de texto y sumarlos.
¿Por qué esto causa dolor físico?
1️⃣ La memoria no es de goma.
f.readlines() vuelca todo el archivo en la RAM. Si el archivo pesa 10 GB, tu servidor dirá «adiós» antes de que termines de leer este post.2️⃣ Filtrado carácter por carácter con lambda. Unir una cadena carácter por carácter con
"".join(filter(...)) es la forma más lenta de procesar cadenas en Python. ¿Estamos programando o ensartando cuentas?3️⃣ Comprensiones de listas anidadas. La legibilidad está al nivel de los jeroglíficos egipcios. Para entender dónde se cierra un paréntesis, hay que llamar a un exorcista.
4️⃣ PEP8 salió del chat. La falta de espacios después de
: y alrededor de los operadores no es ahorrar espacio, es falta de respeto hacia los demás.Conclusión: Obtuvimos un código que funciona lento, consume memoria y es absolutamente ilegible.
✅ ¿Cómo hacerlo de forma humana?
Si necesitas extraer números de un texto, para eso existen las expresiones regulares.
Así es como debería verse este código en el mundo de una persona sana:
import re
def total_sum_from_file(file_path: str) -> float:
total = 0.0
# Usamos un administrador de contexto y un iterador de líneas
with open(file_path, 'r', encoding='utf-8') as f:
for line in f:
# Buscamos todo lo que parezca un número (entero o con punto)
numbers = re.findall(r"[-+]?\d*\.\d+|\d+", line)
total += sum(map(float, numbers))
return total
print(total_sum_from_file("t.txt"))Por qué es mejor así:
1. Legibilidad: Incluso un junior entenderá lo que sucede aquí en 5 segundos.
2. Memoria: Leemos el archivo línea por línea. Si el archivo pesa 10 GB, este código no fallará.
3. Velocidad:
re.findall a nivel C funciona más rápido que tu filtro carácter por carácter en Python.#código_fumador
Comentarios
0Aún no hay comentarios.