""

miércoles, 15 de abril de 2026

Python II. Modulo Random. Fuente: Python Institute

Random, es un adjetivo del ingles que traduce aleatorio (al azar), si estas interesado en el aprendizaje del idioma ingles te invito a visitar este blog, https://learning-english-in-colombia.blogspot.com/ 


1.2.3 ¿Existe aleatoriedad real en las computadoras?

Otro módulo que vale la pena mencionar es el que se llama random, que significa aleatorio.

Ofrece algunos mecanismos que permiten operar con números pseudoaleatorios.

Toma en cuenta el prefijo pseudo - los números generados por los módulos pueden parecer aleatorios en el sentido de que no se pueden predecir, pero no hay que olvidar que todos se calculan utilizando algoritmos muy refinados.

Los algoritmos no son aleatorios, son deterministas y predecibles. Solo aquellos procesos físicos que se salgan completamente de nuestro control (como la intensidad de la radiación cósmica) pueden usarse como fuente de datos aleatorios reales. Los datos producidos por computadoras deterministas no pueden ser aleatorios de ninguna manera.

Un generador de números aleatorios toma un valor llamado semilla, lo trata como un valor de entrada, calcula un número "aleatorio" basado en él (el método depende de un algoritmo elegido) y produce una nueva semilla.

La duración de un ciclo en el que todos los valores semilla son únicos puede ser muy largo, pero no es infinito: tarde o temprano los valores iniciales comenzarán a repetirse y los valores generadores también se repetirán. Esto es normal. Es una característica, no un error.

El valor de la semilla inicial, establecido durante el inicio del programa, determina el orden en que aparecerán los valores generados.

El factor aleatorio del proceso puede ser aumentado al establecer la semilla tomando un número de la hora actual - esto puede garantizar que cada ejecución del programa comience desde un valor semilla diferente (por lo tanto, usará diferentes números aleatorios).

Afortunadamente, Python realiza dicha inicialización al importar el módulo.

1.2.4 Funciones selectas del módulo random

La función random

La función general llamada random() (no debe confundirse con el nombre del módulo) produce un número flotante x entre el rango (0.0, 1.0) - en otras palabras: (0.0 <= x < 1.0).

El programa de ejemplo a continuación producirá cinco valores pseudoaleatorios - ya que sus valores están determinados por el valor semilla actual (bastante impredecible), no puedes adivinarlos:

>>from random import random

>>for i in range(5):

>>    print(random())

>>>

0.0526319405023542

0.3923452760242002

0.85131849140358

0.5547143821051266

0.7919790097820241

La función seed

La función seed() es capaz de directamente establecer la semilla del generador. Te mostramos dos de sus variantes:

  • seed() - establece la semilla con la hora actual.
  • seed(int_value) - establece la semilla con el valor entero int_value.

Hemos modificado el programa anterior; de hecho, hemos eliminado cualquier rastro de aleatoriedad del código:

>>from random import random, seed

>>seed(0)

>>for i in range(5):

>>    print(random())

 >>>

0.844421851525

0.75795440294

0.420571580831

0.258916750293

0.511274721369

¿Y tú?

Nota: tus valores pueden ser ligeramente diferentes si tu sistema utiliza aritmética de punto flotante más precisa o menos precisa, pero la diferencia se verá bastante lejos del punto decimal.

Las funciones randrange y randint

Si deseas valores aleatorios enteros, una de las siguientes funciones encajaría mejor:

  • randrange(fin)
  • randrange(inicio, fin)
  • randrange(inicio, fin, incremento)
  • randint(izquiera, derecha)

Las primeras tres invocaciones generarán un valor entero tomado (pseudoaleatoriamente) del rango:

  • range(fin)
  • range(inicio, fin)
  • range(inicio, fin, incremento)

Toma en cuenta la exclusión implícita del lado derecho.

La última función es equivalente a randrange(izquierda, derecha+1) - genera el valor entero i, el cual cae en el rango [izquierda, derecha] (sin exclusión en el lado derecho).

Observa el código en el editor. Este programa generará una línea que consta de tres ceros y un cero o un uno en el cuarto lugar.

>>from random import randrange, randint

>>print(randrange(1), end=' ')

>>print(randrange(0, 1), end=' ')

>>print(randrange(0, 1, 1), end=' ')

>>print(randint(0, 1))

>>>

0000

Las funciones anteriores tienen una desventaja importante - pueden producir valores repetidos incluso si el número de invocaciones posteriores no es mayor que el rango especificado.

Observa el código en el editor - Es muy probable que el programa genere un conjunto de números en el que algunos elementos no sean únicos:

>>from random import randint

>>for i in range(10):

>>    print(randint(1, 10), end=',')

>>>
9,4,5,4,5,8,9,4,8,4,

Las funciones choice y sample

Como puedes ver, esta no es una buena herramienta para generar números para la lotería. Afortunadamente, existe una mejor solución que escribir tu propio código para verificar la singularidad de los números "sorteados".

Es una función con el nombre de choice:

  • choice(secuencia)
  • sample(secuencia, elementos_a_elegir=1)

La primera variante elige un elemento "aleatorio" de la secuencia de entrada y lo devuelve.

El segundo crea una lista (una muestra) que consta del elemento elementos_a_elegir (que por defecto es 1) «sorteado» de la secuencia de entrada.

En otras palabras, la función elige algunos de los elementos de entrada, devolviendo una lista con la elección. Los elementos de la muestra se colocan en orden aleatorio. Nota que elementos_a_elegir no debe ser mayor que la longitud de la secuencia de entrada.

Observa el código a continuación:

>>from random import choice, sample

>>my_list = [1, 2, 3, 4, 5, 6, 7, 8, 9, 10]

>>print(choice(my_list))
>>print(sample(my_list, 5))
>>print(sample(my_list, 10))

>>>
4
[3, 1, 8, 9, 10]
[10, 8, 5, 1, 6, 4, 3, 9, 7, 2]


domingo, 12 de abril de 2026

Python II. Introducción a los Módulos en Python

Fuente: Python Institute

1.1.1 ¿Qué es un módulo?

El código de computadora tiene una tendencia a crecer. Podemos decir que el código que no crece probablemente sea completamente inutilizable o esté abandonado. Un código real, deseado y ampliamente utilizado se desarrolla continuamente, ya que tanto las demandas de los usuarios como sus expectativas se desarrollan de manera diferente.

Un código que no puede responder a las necesidades de los usuarios se olvidará rápidamente y se reemplazará instantáneamente con un código nuevo, mejor y más flexible. Se debe estar preparado para esto, y nunca pienses que tus programas están terminados por completo. La finalización es un estado de transición y generalmente pasa rápidamente, después del primer informe de error. Python en sí es un buen ejemplo de cómo actúa esta regla.

El código creciente es, de hecho, un problema creciente. Un código más grande siempre significa un mantenimiento más difícil. La búsqueda de errores siempre es más fácil cuando el código es más pequeño (al igual que encontrar una rotura mecánica es más simple cuando la maquinaria es más simple y pequeña).

Además, cuando se espera que el código que se está creando sea realmente grande (puedes usar el número total de líneas de código como una medida útil, pero no muy precisa, del tamaño del código) entonces, se deseará, o más bien, habrá la necesidad de dividirlo en muchas partes, implementado en paralelo por unos cuantos, una docena, varias docenas o incluso varios cientos de desarrolladores.

Por supuesto, esto no se puede hacer usando un archivo fuente grande, el cual esta siendo editado por todos los programadores al mismo tiempo. Esto seguramente conducirá a un desastre.

Si se desea que dicho proyecto de software se complete con éxito, se deben tener los medios que permitan:
  • Dividir todas las tareas entre los desarrolladores.
  • Después, unir todas las partes creadas en un todo funcional. 
  • Por ejemplo, un determinado proyecto se puede dividir en dos partes principales: La interfaz de usuario (la parte que se comunica con el usuario mediante widgets y una pantalla gráfica).
La lógica (la parte que procesa los datos y produce resultados).

Cada una de estas partes se puede (muy probablemente) dividir en otras más pequeñas, y así sucesivamente. Tal proceso a menudo se denomina descomposición.

Por ejemplo, si te pidieran organizar una boda, no harías todo tú mismo: encontrarías una serie de profesionales y dividirías la tarea entre todos.

¿Cómo se divide una pieza de software en partes separadas pero cooperantes? Esta es la pregunta. Los módulos son la respuesta.
1.1.2 ¿Cómo hacer uso de un módulo?

Entonces, ¿qué es un módulo? El Tutorial de Python lo define como un archivo que contiene definiciones y sentencias de Python, que se pueden importar más tarde y utilizar cuando sea necesario.

El manejo de los módulos consta de dos cuestiones diferentes:

  • El primero (probablemente el más común) ocurre cuando se desea utilizar un módulo ya existente - escrito por otra persona o creado por el programador mismo en algún proyecto complejo: en este caso, se considera al programador como el usuario del módulo.
  • El segundo ocurre cuando se desea crear un nuevo módulo, ya sea para uso propio o para facilitar la vida de otros programadores - aquí tu eres el proveedor del módulo.

Discutamos ambos por separado.

En primer lugar, un módulo se identifica por su nombre. Si se desea utilizar cualquier módulo, se necesita saber su nombre. Se entrega una cantidad (bastante grande) de módulos junto con Python. Se puede pensar en ellos como una especie de “equipamiento adicional de Python”.

Todos estos módulos, junto con las funciones integradas, forman la Biblioteca Estándar de Python - un tipo especial de biblioteca donde los módulos desempeñan el papel de libros (incluso podemos decir que las carpetas desempeñan el papel de estanterías). Si deseas ver la lista completa de todos los «volúmenes» recopilados en esa biblioteca, se puede encontrar aquí: https://docs.python.org/3/library/index.html.

Cada módulo consta de entidades (como un libro consta de capítulos). Estas entidades pueden ser funciones, variables, constantes, clases y objetos. Si se sabe como acceder a un módulo en particular, se puede utilizar cualquiera de las entidades que almacena.

Comencemos la discusión con uno de los módulos más utilizados, el que lleva por nombre math. Su nombre habla por sí mismo - el módulo contiene una rica colección de entidades (no solo funciones) que permiten a un programador implementar efectivamente cálculos que exigen el uso de funciones matemáticas, como sen() o log().

1.1.3 Importando un módulo

Para que un módulo sea utilizable, hay que importarlo (piensa en ello como sacar un libro del estante). La importación de un módulo se realiza mediante una instrucción llamada import. Nota: import es también una palabra clave reservada (con todas sus implicaciones).

Supongamos que deseas utilizar dos entidades proporcionadas por el módulo math:

  • Un símbolo (constante) que representa un valor preciso (tan preciso como sea posible usando aritmética de punto flotante doble) de π (aunque usar una letra griega para nombrar una variable es totalmente posible en Python, el símbolo se llama pi - es una solución más conveniente, especialmente para esa parte del mundo que ni tiene ni va a usar un Teclado Griego).
  • Una función llamada sin() (el equivalente informático de la función matemática seno).

Ambas entidades están disponibles a través del módulo math, pero la forma en que se pueden usar depende en gran medida de como se haya realizado la importación.

La forma más sencilla de importar un módulo en particular es usar la instrucción para importar de la siguiente manera:

import math
 

La cláusula contiene:

  • La palabra reservada import;
  • El nombre del módulo que se va a importar.

La instrucción puede colocarse en cualquier parte del código, pero debe colocarse antes del primer uso de cualquiera de las entidades del módulo.

Si quiere (o tiene que) importar más de un módulo, puede hacerlo repitiendo la cláusula import (preferida):

import math
import sys

o enumerando los módulos después de la palabra clave reservada import, como aquí:

import math, sys

La instrucción importa dos módulos, primero uno llamado math y luego un segundo llamado sys.

La lista de módulos puede ser arbitrariamente larga.

1.1.4 Namespace

Para continuar, debes familiarizarte con un término importante: namespace. No te preocupes, no entraremos en detalles - esta explicación será lo más breve posible.

Un namespace es un espacio (entendido en un contexto no físico) en el que existen algunos nombres y los nombres no entran en conflicto entre sí (es decir, no hay dos objetos diferentes con el mismo nombre). Podemos decir que cada grupo social es un namespace - el grupo tiende a nombrar a cada uno de sus miembros de una manera única (por ejemplo, los padres no darían a sus hijos el mismo nombre).

Esta singularidad se puede lograr de muchas maneras, por ejemplo, mediante el uso de apodos junto con los nombres (funcionará dentro de un grupo pequeño como una clase en una escuela) o asignando identificadores especiales a todos los miembros del grupo (el número de Seguro Social de EE. UU. es un buen ejemplo de tal práctica).

Dentro de un determinado namespace, cada nombre debe permanecer único. Esto puede significar que algunos nombres pueden desaparecer cuando cualquier otra entidad de un nombre ya conocido ingresa al namespace. Mostraremos como funciona y como controlarlo, pero primero, volvamos a las importaciones.

Si el módulo de un nombre especificado existe y es accesible (un módulo es de hecho un archivo fuente de Python), Python importa su contenido, se hacen conocidos todos los nombres definidos en el módulo, pero no ingresan al namespace del código.

Esto significa que puedes tener tus propias entidades llamadas sin o pi y no serán afectadas en alguna manera por la importación.

En este punto, es posible que te estés preguntando como acceder al pi el cual viene del módulo math.

Para hacer esto, se debe de mandar llamar el pi con el nombre del módulo original.

1.1.5 Importando un módulo: continuación

Este primer ejemplo no será muy avanzado - solo se desea imprimir el valor de sin(½π).

Observa el código en el editor. Así es como se prueba.

  • light_modedark_mode
import math print(math.sin(math.pi/2))
Console sync

>>import math

>>print(math.sin(math.pi/2))

El código genera el valor esperado: 1.0.

Observa el fragmento a continuación, esta es la forma en que se habilitan los nombres de pi y sin con el nombre de su módulo de origen:

math.pi
math.sin

Es sencillo, se coloca:

  • El nombre del módulo (math).
  • Un punto (p,ej., .).
  • El nombre de la entidad (pi).

Tal forma indica claramente el namespace en el que existe el nombre.

Nota: el uso de esto es obligatorio si un módulo ha sido importado con la instrucción import. No importa si alguno de los nombres del código y del namespace del módulo están en conflicto o no.

Nota: el eliminar cualquiera de las dos indicaciones del nombre del módulo hará que el código sea erróneo. No hay otra forma de entrar al namespace de math si se hizo lo siguiente:

import math

Ahora te mostraremos cómo pueden dos namespaces (el tuyo y el del módulo) coexistir.

Echa un vistazo al ejemplo en la ventana del editor.

Hemos definido nuestros propios pi y sin aquí.

  • light_modedark_mode
Console sync

>>import math   # importacion del modulo

>>def sin(x):  # se define la funcion                                                                                

>>    if 2 * x == pi:  # condicional del if

>>        return 0.99999999    # si el condicional se cumple

>>    else:  # si el condicional no se cumple

>>        return None

>>pi = 3.14   # se define la variable pi

>>print(sin(pi/2))  # se muestra por pantalla el resultado de la funcion

>>print(math.sin(math.pi/2))  # se muestra el resultado del modulo

Ejecuta el programa. El código debe producir la siguiente salida:

Output
0.99999999
1.0

Como puedes ver, las entidades no se afectan entre sí.

En el segundo método, la sintaxis del import señala con precisión que entidad (o entidades) del módulo son aceptables en el código:

from math import pi

La instrucción consta de los siguientes elementos:

  • La palabra clave reservada from.
  • El nombre del módulo a ser (selectivamente) importado.
  • La palabra clave reservada import.
  • El nombre o lista de nombres de la entidad o entidades las cuales estan siendo importadas al namespace.

La instrucción tiene este efecto:

  • Las entidades listadas son las únicas que son importadas del módulo indicado.
  • Los nombres de las entidades importadas pueden ser accedidas dentro del código sin especificar el nombre del módulo de origen.

Nota: no se importan otras entidades, únicamente las especificadas. Además, no se pueden importar entidades adicionales utilizando - una línea como esta:

print(math.e)

Esto ocasionará un error, (e es la constante de Euler: 2.71828...)

Reescribamos el código anterior para incorporar esta nueva técnica.

Aquí está:

  • light_modedark_mode
Console sync

>>from math import sin, pi

>>print(sin(pi/2))

>>>
1.0

El resultado debe de ser el mismo que el anterior, se han empleado las mismas entidades: 1.0. Copia y pega el código en el editor, y ejecuta el programa.

¿El código parece más simple? Quizás, pero el aspecto no es el único efecto de este tipo de importación. Veamos más a detalle esto.

Observa el código en el editor. Analízalo cuidadosamente:

  • La línea 01: lleva a cabo la importación selectiva.
  • La línea 03: hace uso de las entidades importadas y obtiene el resultado esperado (1.0).
  • Las líneas 05 a la 12: redefinen el significado de pi y sin - en efecto, reemplazan las definiciones originales (importadas) dentro del namespace del código.
  • La línea 15: retorna 0.99999999, lo cual confirma nuestras conclusiones.
  • light_modedark_mode
Console sync

Hagamos otra prueba. Observa el código a continuación:

  • light_modedark_mode
Console sync

Aquí, se ha invertido la secuencia de las operaciones del código:

  • Las líneas del 01 al 08: definen nuestro propio pi y sin.
  • La línea 11: hace uso de ellas (0.99999999 aparece en pantalla).
  • La línea 13: lleva a cabo la importación - los símbolos importados reemplazan sus definiciones anteriores dentro del namespace.
  • La línea 15: retorna 1.0 como resultado.
1.1.6 Importando un módulo: *

En el tercer método, la sintaxis del import es una forma más agresiva que la presentada anteriormente:

from module import *
 

Como puedes ver, el nombre de una entidad (o la lista de nombres de entidades) se reemplaza con un solo asterisco (*).

Tal instrucción importa todas las entidades del módulo indicado.

¿Es conveniente? Sí, lo es, ya que libera del deber de enumerar todos los nombres que se necesiten.

¿Es inseguro? Sí, a menos que conozcas todos los nombres proporcionados por el módulo, es posible que no puedas evitar conflictos de nombres. Trata esto como una solución temporal e intenta no usarlo en un código regular.

1.1.7 La palabra clave as

Si se importa un módulo y no se esta conforme con el nombre del módulo en particular (por ejemplo, si es el mismo que el de una de sus entidades ya definidas) puede dársele otro nombre: esto se llama aliasing o renombrado.

Aliasing (renombrado) hace que el módulo se identifique con un nombre diferente al original. Esto también puede acortar los nombres originales.

La creación de un alias se realiza junto con la importación del módulo, y exige la siguiente forma de la instrucción import:

import module as alias
 

El «module» identifica el nombre del módulo original mientras que el «alias» es el nombre que se desea usar en lugar del original.

Nota: as es una palabra clave reservada.

1.1.8 Aliasing (renombrado)

Si necesitas cambiar la palabra math, puedes introducir tu propio nombre, como en el ejemplo:

import math as m
    
print(m.sin(m.pi/2))
 

Nota: después de la ejecución exitosa de una importación con alias, el nombre original del módulo se vuelve inaccesible y no debe ser utilizado.

A su vez, cuando usa la variante from module import name y se necesita cambiar el nombre de la entidad, se crea un alias para la entidad. Esto hará que el nombre sea reemplazado por el alias que se elija.

Así es como se puede hacer:

from module import name as alias
 

Como anteriormente, el nombre original (sin alias) se vuelve inaccesible.

La frase name as alias puede repetirse: puedes emplear comas para separar las frases, como a continuación:

from module import n as a, m as b, o as c
  

El ejemplo puede parecer un poco extraño, pero funciona:

from math import pi as PI, sin as sine
  
print(sine(PI/2))
  

Ahora estás familiarizado con los conceptos básicos del uso de módulos. Permítenos mostrarte algunos módulos y algunas de sus entidades útiles.


1.1.9 RESUMEN DE LA SECCIÓN

1. Si deseas importar un módulo como un todo, puedes hacerlo usando la sentencia import nombre_del_módulo. Puedes importar más de un módulo a la vez utilizando una lista separada por comas. Por ejemplo:

import mod1
import mod2, mod3, mod4
   

Aunque la última forma no se recomienda por razones estilísticas, y es mejor y más bonito expresar la misma intención de una forma más detallada y explícita, como por ejemplo:

import mod2
import mod3
import mod4
  

2. Si un módulo se importa de la manera anterior y desea acceder a cualquiera de sus entidades, debes anteponer el nombre de la entidad empleando la notación con punto. Por ejemplo:

import my_module
   
result = my_module.my_function(my_module.my_data)
 

El fragmento de código utiliza dos entidades que provienen del módulo my_module: una función llamada my_function() y una variable con el nombre my_data. Ambos nombres deben tener el prefijo my_module. Ninguno de los nombres de entidad importados entra en conflicto con los nombres idénticos existentes en el namespace de tu código.

3. Se te permite no solo importar un módulo como un todo, sino también importar solo entidades individuales de él. En este caso, las entidades importadas no deben especificar el prefijo cuando son empleadas. Por ejemplo:

from module import my_function, my_data
  
result = my_function(my_data)
 

La forma anterior, a pesar de su atractivo, no se recomienda debido al peligro de causar conflictos con los nombres derivados de la importación del namespace del código.

4. La forma más general de la sentencia anterior te permite importar todas las entidades ofrecidas por un módulo:

from my_module import *
  
result = my_function(my_data)
 

Nota: la variante de esta importación no se recomienda debido a las mismas razones que antes (la amenaza de un conflicto de nombres es aún más peligrosa aquí).

5. Puedes cambiar el nombre de la entidad importada "sobre la marcha" utilizando la frase as del import. Por ejemplo:

from module import my_function as fun, my_data as dat
  
result = fun(dat)
 

1.1.10 CUESTIONARIO DE SECCIÓN

Pregunta 1: Quieres invocar la función make_money() contenida en el módulo llamado mint. Tu código comienza con la siguiente línea:

import mint

¿Cuál es la forma adecuada de invocar a la función?

Pregunta 2: Deseas invocar la función make_money() contenida en el módulo llamado mint. Tu código comienza con la siguiente línea:

from mint import make_money
   

¿Cuál es la forma adecuada de invocar a la función?

Pregunta 3: Has escrito una función llamada make_money por tu cuenta. Necesitas importar una función con el mismo nombre del módulo mint y no deseas cambiar el nombre de ninguno de tus nombres previamente definidos. ¿Qué variante de la sentencia import puede ayudarte con el problema?

Pregunta 4: ¿Qué forma de invocación de la función make_money es válida si tu código comienza con la siguiente línea?

from mint import *
 

Entradas recientes

Python II. Modulo Random. Fuente: Python Institute

Random, es un adjetivo del ingles que traduce aleatorio (al azar), si estas interesado en el aprendizaje del idioma ingles te invito a visi...

Entradas Populares