Type hints en Python: escribe código más claro

Publicado el: 11/07/2026
Tempo de leitura: 4 minutos
Introdução ao uso de type hints em Python

Los type hints, o anotaciones de tipo, permiten describir qué datos espera y devuelve el código Python. No convierten a Python en un lenguaje de tipado estático ni validan automáticamente todos los valores, pero mejoran autocompletado, documentación, revisión y detección temprana de errores.

Primeras anotaciones

Una función puede anotar parámetros y retorno:

def saludar(nombre: str, veces: int = 1) -> str:
    return " ".join([f"Hola, {nombre}"] * veces)

Los editores pueden advertir si alguien pasa una lista donde se esperaba una cadena. Para repasar la estructura, consulta la guía de funciones en Python.

Tipos básicos y colecciones

Se pueden anotar str, int, float, bool y colecciones:

def promedio(valores: list[float]) -> float:
    return sum(valores) / len(valores)

def contar(textos: tuple[str, ...]) -> dict[str, int]:
    return {texto: len(texto) for texto in textos}

Las formas modernas como list[str] funcionan en versiones recientes de Python. Proyectos compatibles con versiones antiguas pueden utilizar equivalentes del módulo typing.

Optional y valores None

Si un valor puede ser una cadena o None, exprésalo:

def buscar_usuario(usuario_id: int) -> str | None:
    if usuario_id == 1:
        return "Ana"
    return None

Esto obliga a quien llama a considerar la ausencia de resultado. La guía sobre return en Python explica cómo diseñar resultados previsibles.

Union y alias de tipo

Un valor puede aceptar más de un tipo:

Identificador = int | str

def normalizar_id(valor: Identificador) -> str:
    return str(valor).strip()

Los alias mejoran legibilidad cuando una combinación se repite. No crees alias para conceptos triviales; úsalos cuando expresen una idea del dominio.

TypedDict y datos estructurados

Para diccionarios con claves conocidas, TypedDict es más preciso que dict[str, object]:

from typing import TypedDict

class Usuario(TypedDict):
    nombre: str
    edad: int
    activo: bool

def mostrar(usuario: Usuario) -> str:
    return f"{usuario['nombre']} - {usuario['edad']}"

En estructuras más complejas también conviene considerar dataclasses o modelos de validación.

Callable para funciones

Cuando una función recibe otra función, Callable describe la firma:

from collections.abc import Callable

def aplicar(
    operacion: Callable[[int, int], int],
    a: int,
    b: int
) -> int:
    return operacion(a, b)

Este patrón aparece en callbacks y decoradores. La guía de decoradores en Python muestra casos donde las anotaciones se vuelven especialmente útiles.

Genéricos con TypeVar

Un genérico conserva la relación entre entrada y salida:

from typing import TypeVar

T = TypeVar("T")

def primero(elementos: list[T]) -> T:
    if not elementos:
        raise ValueError("La lista está vacía")
    return elementos[0]

Si se recibe una lista de cadenas, el resultado se interpreta como cadena. Si se recibe una lista de enteros, el resultado es entero.

Herramientas de análisis

Los type hints ofrecen más valor cuando se ejecuta un analizador como mypy, Pyright o el sistema integrado del editor. Estas herramientas detectan retornos incompatibles, atributos inexistentes y argumentos incorrectos sin ejecutar el código.

La documentación oficial del módulo typing presenta las herramientas disponibles. El PEP 484 describe el sistema original de type hints.

Type hints no son validación

Python normalmente no impide esta llamada en tiempo de ejecución:

def duplicar(numero: int) -> int:
    return numero * 2

duplicar("hola")  # produce "holahola"

La anotación informa, pero no valida. En límites externos, como una API o un archivo, utiliza validación explícita o bibliotecas adecuadas. Por ejemplo, FastAPI usa anotaciones junto con Pydantic para validar solicitudes.

Type hints con *args y **kwargs

También pueden anotarse argumentos flexibles:

def sumar(*valores: float) -> float:
    return sum(valores)

def configurar(**opciones: str) -> dict[str, str]:
    return opciones

La guía de *args y **kwargs explica la mecánica de estos parámetros. La anotación se aplica a cada valor capturado, no a la tupla o diccionario completo de la firma.

Buenas prácticas

Anota las interfaces públicas, funciones reutilizables y estructuras importantes. Evita tipos demasiado generales como Any cuando puedes ser específico. No añadas anotaciones tan complejas que nadie pueda comprenderlas. El objetivo es aclarar el código, no demostrar sofisticación.

Adopta type hints de forma gradual. Empieza por parámetros y retornos, configura un analizador y corrige advertencias relevantes. Las anotaciones bien diseñadas funcionan como documentación ejecutable para herramientas y ayudan a que refactorizaciones grandes sean más seguras.

Protocolos y tipado estructural

Un Protocol describe comportamientos sin exigir herencia directa. Esto es útil cuando varias clases poseen el mismo método, aunque no comparten una clase base.

from typing import Protocol

class Exportable(Protocol):
    def exportar(self) -> str:
        ...

def guardar(objeto: Exportable) -> str:
    return objeto.exportar()

Cualquier objeto con un método compatible puede utilizarse. Este enfoque reduce acoplamiento y encaja con el estilo flexible de Python.

ParamSpec en decoradores

Tipar un decorador genérico es difícil porque debe conservar los parámetros de la función original. ParamSpec representa esa lista de parámetros y permite que el analizador mantenga la firma. No es necesario para empezar, pero resulta valioso en bibliotecas y utilidades compartidas.

Anotaciones y versiones de Python

Las capacidades de typing evolucionan. Antes de adoptar una sintaxis, revisa la versión mínima del proyecto. Un equipo que soporta versiones antiguas puede necesitar importar tipos desde typing_extensions. Mantén la configuración del analizador alineada con la versión ejecutada en producción para evitar advertencias engañosas.

Compartilhe:

Facebook
WhatsApp
Twitter
LinkedIn

Contenido del artículo

    Artículos relacionados

    Uso de dataclasses para simplificar classes em Python
    Buenas Prácticas
    Foto de perfil de Leandro Hirt da Academify

    Dataclasses en Python: clases de datos más limpias

    Aprende dataclasses en Python: campos, valores predeterminados, field, frozen, order, __post_init__, herencia, asdict y buenas prácticas.

    Ler mais

    Tempo de leitura: 4 minutos
    11/07/2026
    Criação de hashes seguros para senhas usando Python
    Buenas Prácticas
    Foto de perfil de Leandro Hirt da Academify

    Hash de contraseñas con bcrypt en Python

    Aprende bcrypt en Python para almacenar contraseñas: salt, coste, hash, verificación, rehash, límites, errores y recomendaciones de seguridad.

    Ler mais

    Tempo de leitura: 5 minutos
    11/07/2026
    Problemas de travamento com threading em scripts Python
    Buenas Prácticas
    Foto de perfil de Leandro Hirt da Academify

    Threading en Python: evita que tus scripts se bloqueen

    Aprende threading en Python: hilos, tareas de entrada y salida, join, locks, colas, ThreadPoolExecutor, errores y límites del GIL.

    Ler mais

    Tempo de leitura: 4 minutos
    11/07/2026
    Dicas para otimizar scripts Python lentos
    Buenas Prácticas
    Foto de perfil de Leandro Hirt da Academify

    Por qué tu script Python es lento y cómo mejorarlo

    Descubre por qué un script Python es lento y cómo mejorarlo con cProfile, timeit, estructuras correctas, generadores y mejores algoritmos.

    Ler mais

    Tempo de leitura: 5 minutos
    11/07/2026
    Leitura de variáveis de ambiente em projetos Python
    Buenas Prácticas
    Foto de perfil de Leandro Hirt da Academify

    Variables de entorno en Python: guía segura

    Aprende a usar variables de entorno en Python, archivos .env, validación, conversión de tipos, secretos, pruebas y buenas prácticas.

    Ler mais

    Tempo de leitura: 4 minutos
    11/07/2026
    Medição de tempo de execução de código Python com timeit
    Buenas Prácticas
    Foto de perfil de Leandro Hirt da Academify

    Timeit en Python: medir el rendimiento correctamente

    Aprende timeit en Python para comparar funciones, repetir benchmarks, separar setup, medir por operación y evitar errores de microoptimización.

    Ler mais

    Tempo de leitura: 5 minutos
    11/07/2026