Saltar al contenido
src / articulos / 02-matematicas_y_funciones.md

Funciones y Matemáticas en Python

Emilio Castro //

En la ingeniería de infraestructura y el desarrollo de software, la repetición manual de código es un antipatrón. Cuando te encuentras escribiendo la misma lógica por tercera vez, es momento de abstraerla. Aquí es donde entran las funciones.

Las funciones en Python son bloques de código reutilizables que aceptan parámetros (entradas), ejecutan una lógica definida y retornan un resultado (salida). Antes de profundizar en su estructura, repasemos brevemente las operaciones aritméticas base, ya que son esenciales para calcular capacidades, latencias o consumo de recursos.

Operaciones Aritméticas Base

# Definamos la capacidad de memoria de dos nodos en GB
node_a_ram = 16
node_b_ram = 32

# Suma: Capacidad total del clúster
print(node_a_ram + node_b_ram)
# Resultado: 48

# Resta: Diferencia de capacidad
print(node_b_ram - node_a_ram)
# Resultado: 16

# Multiplicación: Capacidad total si escalamos node_a a 5 instancias
print(node_a_ram * 5)
# Resultado: 80

# División: Porcentaje de uso si consumimos 12GB en node_b
print(12 / node_b_ram)
# Resultado: 0.375 (37.5%)

Funciones en Python

La sintaxis para definir una función en Python utiliza la palabra reservada def. Como buena práctica, las funciones siempre deben retornar un valor explícito (usando return) para que el bloque que invocó la función pueda procesar el resultado.

def nombre_de_la_funcion(parametros):
    # Lógica de procesamiento
    resultado = "algo calculado"
    return resultado

Para aplicar esto de manera práctica, definiremos funciones que encapsulen cálculos comunes de recursos. Imaginemos que necesitamos calcular el coste de instancias en la nube y determinar cuántos contenedores podemos alojar.

def calcular_coste_mensual(precio_por_hora, horas_activas):
    """Calcula el coste de ejecución mensual de una instancia."""
    return precio_por_hora * horas_activas

def calcular_densidad_contenedores(ram_total_host, ram_por_contenedor):
    """Determina cuántos contenedores caben en un host físico."""
    return ram_total_host / ram_por_contenedor

Una vez definidas, estas funciones pueden ser invocadas en cualquier parte de nuestro script, inyectando los argumentos necesarios en tiempo de ejecución.

# Instancia encendida 730 horas al mes a $0.04 la hora
coste_instancia = calcular_coste_mensual(0.04, 730)
print(f"Coste mensual: ${coste_instancia}")
# Resultado: Coste mensual: $29.2

# Servidor con 64GB de RAM alojando contenedores de 2GB
contenedores_maximos = calcular_densidad_contenedores(64, 2)
print(f"Capacidad máxima de contenedores: {contenedores_maximos}")
# Resultado: Capacidad máxima de contenedores: 32.0

Manejo de Tipos y Errores Básicos

Python es de tipado dinámico, lo que significa que no restringe estrictamente los tipos de datos que se pasan a una función. Si inyectamos un tipo de dato que no soporta la operación matemática definida en la función, el intérprete lanzará una excepción (TypeError).

Por ejemplo, si accidentalmente intentamos calcular la densidad pasando una cadena de texto en lugar de un número:

calcular_densidad_contenedores(64, "dos_gigas")

Resultado en tiempo de ejecución:

TypeError: unsupported operand type(s) for /: ‘int’ and ‘str’

Este error indica que la operación de división (/) no es válida entre un entero (int) y una cadena (str). Más adelante en esta serie abordaremos el manejo de excepciones y la validación de parámetros (sanitización de datos) para construir scripts robustos que no colapsen ante entradas inesperadas.

Dominar las funciones es el primer paso crítico para escribir herramientas de automatización modulares y mantenibles.