Contenido del curso
Fundamentos de Python
Los fundamentos de Python incluyen la sintaxis (sangría para bloques de código), los tipos de datos básicos (numéricos, booleanos, cadenas de texto), las variables, el control de flujo (condicionales como if/elif/else y bucles como for/while), y las funciones (bloques de código reutilizables).
0/6
Operadores y Control de Flujo
Los operadores en Python se clasifican en varios tipos (aritméticos, de comparación, lógicos, de asignación, etc.), mientras que el control de flujo se refiere al orden en que se ejecutan las instrucciones, modificándolo con estructuras como if, elif, else (condicionales), y for o while (bucles). Las instrucciones break, continue y pass también controlan el flujo dentro de los bucles.
0/3
Funciones y Manejo de Errores
Las funciones en Python son bloques de código reutilizables, mientras que el manejo de errores (excepciones) se hace con los bloques try, except, else y finally para gestionar errores de ejecución y evitar que el programa se detenga abruptamente. try ejecuta un código, except lo captura si ocurre un error específico, else se ejecuta si no hay error y finally se ejecuta siempre, haya o no error.
0/3
Estructuras de Datos
Las estructuras de datos principales en Python son las listas, tuplas, diccionarios y conjuntos. Estos tipos de datos se diferencian por su mutabilidad (si sus elementos se pueden cambiar después de su creación) y si mantienen el orden de los elementos. Las listas son ordenadas y mutables, mientras que las tuplas son ordenadas e inmutables. Los diccionarios son colecciones no ordenadas de pares clave-valor, y los conjuntos son colecciones desordenadas de elementos únicos.
0/5
Programación Orientada a Objetos (POO)
La Programación Orientada a Objetos (POO) en Python es un paradigma que organiza el código en torno a objetos, que son instancias de clases. Las clases actúan como plantillas que definen los atributos (datos) y métodos (comportamientos) de los objetos, permitiendo crear programas más modularizados, reutilizables y fáciles de mantener. Python soporta conceptos clave de la POO como la herencia, el encapsulamiento y el polimorfismo.
0/5
Ambientes virtuales
Un entorno virtual de Python es un espacio aislado que permite instalar paquetes y dependencias específicos para un proyecto concreto sin afectar a otras aplicaciones o a la instalación global de Python. Se crea una carpeta con una instalación de Python y una copia local de pip dentro de este entorno, lo que permite a cada proyecto tener sus propias bibliotecas y versiones, evitando así conflictos entre diferentes proyectos que puedan requerir versiones distintas de la misma librería.
0/1
Archivos
El manejo de archivos en Python se realiza principalmente usando la función open() para abrir un archivo y los métodos read(), write(), append() y close() para manipularlo. Es crucial gestionar los archivos adecuadamente, cerrándolos para liberar recursos, aunque es más recomendable usar la sentencia with, que cierra el archivo automáticamente. Python permite trabajar con archivos de texto y binarios, así como con distintos modos de apertura como 'r' (solo lectura), 'w' (escritura/sobreescritura), y 'a' (añadir).
0/1
Módulos y Librerías Estándar
Un "módulo" en Python se refiere a dos conceptos distintos: un archivo .py con código que se puede importar para reutilizar funciones, clases y variables, y el operador % que calcula el residuo de una división entera. Ambos son útiles para organizar el código y resolver problemas matemáticos, respectivamente.
0/2
Hilos y tareas en Python
En Python, los hilos (threads) son secuencias de ejecución dentro de un proceso que permiten la concurrencia, ejecutando tareas simultáneamente para aprovechar mejor los recursos del sistema. Las tareas son las unidades de trabajo a realizar, como descargar archivos o procesar datos. Se utilizan para manejar operaciones que implican espera (I/O-bound) de forma eficiente, permitiendo que una aplicación no se bloquee mientras espera. Para ello, se usa el módulo threading, se crean objetos Thread que representan las tareas, se inician con .start() y se pueden sincronizar con mecanismos como Lock para evitar conflictos.
0/1
Curso de Programación en Pythón 3.

    💡 Declaración y asignación

    Las variables son uno de los conceptos más esenciales en programación.
    Una variable actúa como una etiqueta o contenedor que almacena datos en memoria.
    Nos permite guardar información (como números, texto o resultados de cálculos) y reutilizarla más adelante.

    En Python, las variables se crean de forma muy sencilla: basta con escribir un nombre y asignarle un valor mediante el operador =.


    🧩 Cómo funciona la asignación

    Cuando asignas un valor a una variable, Python realiza internamente tres pasos:

    1. Crea el objeto en memoria (por ejemplo, un número o una cadena).
    2. Asigna ese valor a un nombre (la variable).
    3. Guarda la referencia al objeto en la tabla de nombres.
    mensaje = "Hola mundo"
    numero = 42
    pi = 3.14159
    

    En este ejemplo, las variables mensaje, numero y pi almacenan referencias a objetos de tipo str, int y float respectivamente.

    Podemos comprobar el tipo de dato con la función type():

    print(type(mensaje))  # <class 'str'>
    print(type(numero))   # <class 'int'>
    print(type(pi))       # <class 'float'>
    

    🔢 Asignación de diferentes tipos de datos

    Python permite asignar cualquier tipo de dato a una variable sin necesidad de declarar su tipo previamente.

    TipoEjemploDescripción
    intedad = 25Número entero
    floataltura = 1.75Número decimal
    strnombre = "Javier"Cadena de texto
    booles_estudiante = TrueValor booleano
    listnumeros = [1, 2, 3]Lista mutable
    tuplecoordenadas = (10, 20)Tupla inmutable
    dictpersona = {"nombre": "Ana", "edad": 30}Diccionario

    💡 En Python, el tipo de la variable se infiere automáticamente según el valor asignado.


    🧮 Asignación múltiple y por desempaquetado

    Python permite asignar valores a varias variables en una sola línea, lo que hace el código más limpio y legible.

    👉 Asignación múltiple directa

    x, y, z = 10, 20, 30
    print(x, y, z)  # 10 20 30
    

    👉 Asignación al mismo valor

    a = b = c = 0
    print(a, b, c)  # 0 0 0
    

    👉 Desempaquetado de colecciones

    coordenadas = (5, 10)
    x, y = coordenadas
    print(f"x = {x}, y = {y}")
    

    Incluso puedes ignorar valores usando guiones bajos _:

    nombre, _, edad = ("Lucía", "Madrid", 28)
    print(nombre, edad)
    

    💡 Truco: El guion bajo _ se usa en Python como variable temporal o “de descarte”.


    ⚙️ Asignación con operadores compuestos

    Los operadores de asignación compuesta combinan una operación aritmética con la asignación.
    Son atajos muy utilizados en bucles y contadores.

    OperadorEjemploEquivalente a
    +=x += 3x = x + 3
    -=x -= 2x = x - 2
    *=x *= 5x = x * 5
    /=x /= 2x = x / 2
    //=x //= 2x = x // 2
    **=x **= 2x = x ** 2
    %=x %= 3x = x % 3
    contador = 0
    contador += 1
    contador *= 2
    print(contador)  # 2
    

    🎯 Asignación condicional (expresiones)

    Python 3.8 introdujo el operador “walrus” :=, que permite asignar una variable dentro de una expresión.

    # Ejemplo clásico sin operador :=
    texto = input("Escribe algo: ")
    if texto != "":
        print(f"Has escrito: {texto}")
    
    # Ejemplo con el operador :=
    if (texto := input("Escribe algo: ")) != "":
        print(f"Has escrito: {texto}")
    

    💡 Esto permite escribir código más limpio en bucles o condicionales.


    📘 Resumen de la parte

    • En Python, no se declara el tipo de variable: se infiere automáticamente.
    • La asignación puede ser múltiple, encadenada o por desempaquetado.
    • Los operadores compuestos simplifican el código repetitivo.
    • El operador := permite asignar y evaluar en una sola línea.

    Estos fundamentos son la base de la manipulación de datos en Python.



    ⬆️ Volver al índice

    🔄 Tipado dinámico y mutabilidad

    Python es un lenguaje de tipado dinámico y fuertemente tipado.
    Esto significa que no necesitamos declarar el tipo de una variable, ya que el intérprete lo determina automáticamente según el valor asignado;
    pero, al mismo tiempo, no se permite mezclar tipos incompatibles sin conversión explícita.


    ⚙️ Tipado dinámico en Python

    En lenguajes estáticos como C, C++ o Java, el tipo de variable debe definirse antes de usarla.
    Python, en cambio, detecta el tipo en tiempo de ejecución, permitiendo una mayor flexibilidad.

    x = 10          # x es un int
    x = "Diez"      # ahora es un str
    x = 3.14        # y luego un float
    print(type(x))
    

    Salida:

    
    <class 'float'>
    

    💡 Aunque el tipo cambia, la variable sigue siendo la misma etiqueta que apunta a diferentes objetos en memoria.

    📦 Cómo funciona internamente

    Cuando haces x = 10, Python crea un objeto de tipo int en memoria y hace que x apunte a él.
    Si luego haces x = "hola", x deja de apuntar al número y ahora referencia al nuevo objeto tipo str.

    x = 10
    print(id(x))  # Identificador del objeto en memoria
    x = 20
    print(id(x))  # Nuevo objeto, diferente ID
    

    💡 Los IDs cambian porque los números enteros son inmutables (se crean nuevos objetos al modificarlos).


    🧩 Tipos mutables e inmutables

    En Python, los tipos de datos se dividen según si pueden o no modificarse después de su creación:

    TipoEjemplos¿Mutable?
    Inmutablesint, float, bool, str, tuple❌ No
    Mutableslist, dict, set✅ Sí

    Esto es importante porque afecta cómo las variables comparten o modifican los datos en memoria.


    🔍 Ejemplo de tipo inmutable (str)

    nombre = "Python"
    print(id(nombre))  # ID inicial
    
    nombre += " 3.12"
    print(id(nombre))  # Nuevo ID → se creó un nuevo objeto
    

    Salida:

    
    140254892714352
    140254892726064
    

    💡 Aunque parezca que modificamos la cadena, realmente se creó una nueva en memoria.


    🔧 Ejemplo de tipo mutable (list)

    numeros = [1, 2, 3]
    print(id(numeros))  # ID inicial
    
    numeros.append(4)
    print(id(numeros))  # Mismo ID → se modificó el objeto
    

    Salida:

    
    139944046382720
    139944046382720
    

    ✅ En este caso, el objeto original cambia internamente sin generar uno nuevo.


    🧠 Ejemplos de mutabilidad práctica

    Ejemplo 1: Mutación compartida

    lista1 = [1, 2, 3]
    lista2 = lista1  # Ambas apuntan al mismo objeto
    
    lista2.append(4)
    
    print(lista1)  # [1, 2, 3, 4]
    print(lista2)  # [1, 2, 3, 4]
    

    ⚠️ Como ambas variables apuntan al mismo objeto, el cambio afecta a las dos.
    Para evitarlo, usa una copia con .copy() o list():

    lista1 = [1, 2, 3]
    lista2 = lista1.copy()
    
    lista2.append(4)
    
    print(lista1)  # [1, 2, 3]
    print(lista2)  # [1, 2, 3, 4]
    

    Ejemplo 2: Mutabilidad en funciones

    def agregar_elemento(lista):
        lista.append("nuevo")
    
    datos = ["a", "b"]
    agregar_elemento(datos)
    print(datos)
    

    Salida:

    
    ['a', 'b', 'nuevo']
    

    💡 Como list es mutable, el cambio dentro de la función afecta al objeto original.


    Ejemplo 3: Inmutabilidad en funciones

    def duplicar_valor(x):
        x *= 2
        print("Dentro:", x)
    
    y = 10
    duplicar_valor(y)
    print("Fuera:", y)
    

    Salida:

    
    Dentro: 20
    Fuera: 10
    

    🔒 Como los int son inmutables, el valor global no se ve afectado.


    📋 Recomendaciones para evitar errores comunes

    • 📌 Recuerda que los objetos mutables se comparten por referencia.
      Si quieres una copia independiente, usa copy() o el módulo copy (para copias profundas).
    • 🚫 No uses mutabilidad en parámetros de funciones si no deseas modificar los originales.
    • ✅ Usa inmutables para datos que no deben cambiar, como claves de diccionario o configuraciones.
    • ⚙️ En colecciones anidadas (listas de listas), usa deepcopy() del módulo copy para evitar efectos secundarios.
    import copy
    
    original = [[1, 2], [3, 4]]
    copia_profunda = copy.deepcopy(original)
    
    copia_profunda[0][0] = 99
    
    print(original)       # [[1, 2], [3, 4]]
    print(copia_profunda) # [[99, 2], [3, 4]]
    

    🧾 Resumen de la parte

    • Python usa tipado dinámico: las variables pueden cambiar de tipo en tiempo de ejecución.
    • Los tipos se dividen en mutables (listas, diccionarios, conjuntos) e inmutables (enteros, cadenas, tuplas).
    • Las variables almacenan referencias a objetos, no los objetos en sí.
    • Comprender la mutabilidad evita errores sutiles y pérdidas de datos.


    ⬆️ Volver al índice

    📘 Convenciones de nombres (PEP 8)

    Una de las características más valoradas de Python es su legibilidad.
    La guía oficial de estilo llamada PEP 8 (Python Enhancement Proposal 8) define reglas y convenciones para escribir código limpio, coherente y fácil de mantener.

    Respetar estas normas no solo mejora la comprensión de tu código, sino que también te ayuda a integrarte fácilmente en proyectos colaborativos y profesionales.


    ⚙️ Reglas básicas para nombres de variables

    Antes que nada, las variables deben seguir las siguientes reglas sintácticas:

    ReglaEjemplo válido ✅Ejemplo inválido ❌
    Solo letras, números y guiones bajos (_)nombre_usuarionombre-usuario
    No puede comenzar con un númerousuario11usuario
    No usar espaciosnombre_completonombre completo
    No usar símbolos especiales (@ # $ %)edad_actual@edad
    Python distingue mayúsculas y minúsculasnombreNombre

    💡 Python es case-sensitive, lo que significa que Variable y variable son dos identificadores diferentes.


    🐍 snake_case, PascalCase y CONSTANTES

    Python utiliza diferentes convenciones de nombres según el tipo de elemento que declares:

    ElementoConvenciónEjemplo
    Variables y funcionessnake_casenombre_usuario, calcular_total()
    ConstantesUPPER_CASEPI = 3.1416, MAX_INTENTOS = 3
    ClasesPascalCaseclass Persona:
    Módulos o archivossnake_casegestor_datos.py
    Paquetesminúsculasutilidades

    📘 Ejemplo completo:

    PI = 3.1416  # Constante
    
    def calcular_area(radio):
        return PI * radio ** 2
    
    class Circulo:
        def __init__(self, radio):
            self.radio = radio
            self.area = calcular_area(radio)
    

    🧠 Nombres descriptivos y significativos

    Los nombres deben comunicar claramente la intención de la variable.
    Evita abreviaciones crípticas o letras sueltas, y prefiere nombres autodescriptivos.

    Malo ❌Bueno ✅
    x, y, zcoordenada_x, coordenada_y
    ttemperatura
    resresultado
    calccalcular_promedio

    💡 La legibilidad vale más que la brevedad. Un nombre largo pero claro es mejor que uno corto y confuso.


    🔠 Prefijos, sufijos y casos especiales

    Existen algunas convenciones especiales que Python usa internamente:

    FormaUso habitualEjemplo
    _variableIndica uso interno o privado_resultado_temporal
    __variableActiva name mangling (atributo «protegido»)__contador
    __nombre__Reservado para métodos especiales de Python__init__, __str__
    class Cuenta:
        def __init__(self, saldo):
            self.__saldo = saldo  # atributo "protegido"
    
        def mostrar_saldo(self):
            print(self.__saldo)
    

    💡 El doble guion bajo (__) antes del nombre activa una conversión automática de nombres para evitar colisiones entre clases heredadas (name mangling).


    🚫 Evitar conflictos con palabras reservadas o funciones integradas

    Python tiene un conjunto de palabras reservadas que no se pueden usar como nombres de variables:

    import keyword
    print(keyword.kwlist)
    

    Salida (Python 3.12):

    
    ['False', 'None', 'True', 'and', 'as', 'assert', 'async', 'await',
     'break', 'class', 'continue', 'def', 'del', 'elif', 'else', 'except',
     'finally', 'for', 'from', 'global', 'if', 'import', 'in', 'is', 'lambda',
     'nonlocal', 'not', 'or', 'pass', 'raise', 'return', 'try', 'while', 'with', 'yield']
    

    Además, evita sobrescribir funciones integradas como:

    No usar como variableMotivo
    listReemplaza la clase incorporada list()
    strBloquea el constructor de cadenas
    sumOculta la función sum()
    maxReemplaza la función max()

    Ejemplo de error común:

    list = [1, 2, 3]
    print(list(4, 5, 6))  # ❌ TypeError: 'list' object is not callable
    

    💡 Siempre elige nombres únicos y específicos. Si necesitas usar una palabra parecida, agrégale un sufijo o prefijo: lista_datos, texto_str, etc.


    🧾 Resumen de la parte

    • Usa snake_case para variables y funciones.
    • Usa PascalCase para clases.
    • Usa MAYÚSCULAS para constantes globales.
    • Evita palabras reservadas e identificadores integrados.
    • Prioriza la claridad por encima de la brevedad.
    • Respeta las convenciones PEP 8 para mantener código legible y profesional.


    ⬆️ Volver al índice

    🧱 Uso de constantes, comentarios y documentación mínima

    En esta última parte de la lección sobre variables y buenas prácticas, aprenderás cómo definir correctamente constantes, escribir comentarios útiles y documentar tus funciones y módulos de forma profesional.


    🔠 Definición y convención de constantes

    Python no tiene un tipo de dato especial para las constantes.
    Por convención, se consideran constantes aquellas variables cuyo valor no debería cambiar durante la ejecución del programa.

    Según la guía PEP 8, las constantes se escriben en MAYÚSCULAS_CON_GUIONES_BAJOS y suelen declararse al inicio del archivo o módulo.

    # Constantes globales (por convención)
    PI = 3.1416
    MAX_INTENTOS = 3
    MENSAJE_BIENVENIDA = "Bienvenido al sistema"
    URL_API = "https://api.ejemplo.com/v1"
    

    💡 Aunque técnicamente pueden modificarse, no deben hacerlo por principios de diseño.
    Por eso se escriben en mayúsculas, como recordatorio visual.


    📍 Ubicación y ámbito de las constantes

    Las constantes se suelen definir:

    1. En la parte superior de un script o módulo.
    2. En un archivo separado (por ejemplo, config.py) para centralizar su gestión.

    Ejemplo en archivo principal:

    # archivo: main.py
    from config import PI, MAX_INTENTOS
    
    def calcular_area(radio):
        return PI * radio ** 2
    
    print(calcular_area(5))
    

    Ejemplo de archivo de configuración:

    # archivo: config.py
    PI = 3.1416
    MAX_INTENTOS = 3
    APP_NAME = "Mi Aplicación"
    

    💡 Esto mejora la mantenibilidad del proyecto y facilita las modificaciones futuras sin alterar el código principal.


    🧮 Uso del módulo enum para constantes enumeradas

    Para conjuntos limitados de valores, como días de la semana o estados de un proceso, se recomienda usar el módulo estándar enum.

    from enum import Enum
    
    class EstadoPedido(Enum):
        PENDIENTE = 1
        EN_PROCESO = 2
        ENVIADO = 3
        ENTREGADO = 4
    
    print(EstadoPedido.ENVIADO.name)  # 'ENVIADO'
    print(EstadoPedido.ENVIADO.value) # 3
    

    💡 Las enumeraciones aportan claridad y evitan errores por valores “mágicos” en el código.


    ⚙️ Constantes en configuración y entorno

    En proyectos reales, es común usar variables de entorno o archivos .env para guardar datos sensibles (como contraseñas, tokens o URLs).

    # archivo: config.py
    import os
    
    API_KEY = os.getenv("API_KEY", "clave_por_defecto")
    MODO_DEBUG = os.getenv("DEBUG", "False") == "True"
    

    💡 Esto permite configurar el comportamiento del programa sin modificar el código fuente.


    📝 Buenas prácticas de comentarios y documentación mínima

    Los comentarios son esenciales para explicar el propósito y la lógica de tu código.
    Sin embargo, deben usarse con criterio: menos es más.
    Un código bien escrito se explica por sí mismo, y los comentarios deben aportar contexto adicional, no repetir lo evidente.


    💬 Tipos de comentarios

    TipoUsoEjemplo
    Comentario en líneaExplica una instrucción puntualx = x + 1 # Incrementa el contador
    Comentario de bloqueDescribe secciones completas o algoritmos# Calcula la media aritmética de una lista
    Comentario de documentación (docstring)Describe el propósito de una función, clase o módulo"""Devuelve el área de un círculo dado su radio."""

    📚 Ejemplo práctico: función documentada

    def calcular_promedio(numeros):
        """
        Calcula el promedio de una lista de números.
    
        Parámetros:
            numeros (list): Lista de números (int o float).
    
        Retorna:
            float: Valor promedio de la lista.
        """
        if not numeros:
            return 0.0
        return sum(numeros) / len(numeros)
    
    valores = [8, 9, 10]
    print(calcular_promedio(valores))
    

    💡 Los docstrings se pueden leer con la función help() o inspeccionarse con herramientas de documentación automática como Sphinx o pydoc.

    help(calcular_promedio)
    

    ✍️ Comentarios útiles vs innecesarios

    ❌ Mal comentario✅ Buen comentario
    # Suma 1 a x# Incrementa el contador para pasar al siguiente usuario
    # Imprime el resultado# Muestra el total de ventas del mes actual
    # Crear variable# Inicializa la lista de productos disponibles

    💬 Los buenos comentarios explican el por qué, no el qué.


    🧾 Documentación de módulos y scripts

    Al inicio de cada script o módulo, incluye un bloque de documentación general:

    """
    Módulo: gestor_clientes.py
    Autor: Javier Cachón Garrido
    Descripción:
        Contiene funciones para registrar, buscar y eliminar clientes
        en la base de datos SQLite de la aplicación principal.
    Versión: 1.0
    """
    

    💡 Esta práctica profesional ayuda a otros desarrolladores (¡y a ti mismo en el futuro!) a comprender rápidamente la función del archivo.


    🧩 Documentación automática con doctrinas y herramientas

    • 📄 Usa docstrings estándar en triple comillas.
    • 🧭 Sigue el formato Google Style o reStructuredText si planeas generar documentación.
    • 🔧 Herramientas como Sphinx, pdoc o mkdocs pueden convertir tus docstrings en documentación HTML profesional.

    📋 Resumen de la parte

    • Define constantes en mayúsculas al inicio del script o módulo.
    • Centraliza valores fijos en un archivo config.py para mantener orden y claridad.
    • Usa comentarios solo cuando sean necesarios y aporten valor.
    • Documenta funciones, clases y módulos con docstrings claros y concisos.
    • Sigue la guía de estilo PEP 8 para mantener uniformidad y profesionalismo.


    ⬆️ Volver al índice

    Nuestra puntuación
    ¡Haz clic para puntuar esta entrada!
    (Votos: 0 Promedio: 0)
    Scroll al inicio