Procesos Estocásticos y Cadenas de Markov · Tema 13

Simulación de procesos de Poisson

Receta completa: sortear esperas Exp(λ), acumular hasta T, verificar con media ≈ varianza ≈ λT.

01 · Punto de partida

De la teoría al generador

Ya sabemos qué es Poisson (Tema 8), qué es λ (Tema 9) y que las esperas son Exp(λ) sin memoria (Temas 11–12). Falta cerrar el círculo: generar arribos en la computadora que cumplan todo eso.

La receta es corta y exacta: se sortean esperas exponenciales y se acumulan hasta el horizonte. Con semilla es repetible; sin ella, cada corrida es otra historia del mismo proceso.

  • ¿Cómo se sortea una espera Exp(λ) con un uniforme?
  • ¿Cuándo se frena: al superar T?
  • ¿Cómo sé que el generador anda: qué test pasa?
  • ¿Cómo lo hago repetible sin congelar el azar?

02 · Definición

La receta en tres pasos

Todo simulador Poisson homogéneo hace lo mismo:

1

Sortear

S = −ln(1−u)/λ con u ~ U(0,1). Cada espera nace del uniforme.

2

Acumular

Tₖ = Tₖ₋₁ + Sₖ hasta superar T. Los Tₖ ≤ T son los arribos.

3

Verificar

En R réplicas: media(N) ≈ var(N) ≈ λT. Si falla, el código falla.

Complejidad proporcional a los eventos (λT por réplica): con λT = 1000 y R = 1000 hay un millón de sorteos. Para tasas enormes conviene el método normal o directo Po(λT) por conteo.

Entradas y salidas del simulador.
PiezaQué esEjemplo
Entradasλ, T, semilla2/hora, 10 h, 7
MotorEsperas Exp(λ) acumuladas0,4 – 1,1 – 2,7…
SalidasLista Tₖ y N(t)N(10) = 19 arribos
Testmedia ≈ var ≈ λT20 ≈ 21 ≈ 20 ✓

03 · Anatomía

Semilla, horizonte y costo

Cuatro decisiones de ingeniería del simulador:

Semilla
Fija la secuencia para depurar y publicar; se varía para estimar. Una figura = una semilla declarada.
Horizonte T
Condición de freno: se acumula mientras Tₖ ≤ T. El último sorteo que supera T se descarta.
Réplicas R
Una réplica es una historia; R = 300+ estima media y varianza. Más R, menos ruido.
Costo λ·T·R
Cantidad de exponenciales sorteadas. Si explota, se muestrea N(T) ~ Po(λT) directo y se uniformizan los instantes.

Por esperas

Exacto y simple

Acumula Exp(λ). Ideal hasta miles de eventos por réplica.

Por conteo directo

Rápido a gran escala

Sortea N ~ Po(λT) y ubica N uniformes en [0,T]. Mismo proceso, menos sorteos.

04 · Ejemplos

Simuladores que usarás ya

La misma receta con distintos λ y T:

(λ, T, semilla)→arribos→N(t)
  1. 1
    Call center (λ = 15/h, T = 8 h).

    ~120 arribos por réplica para dimensionar turnos.

  2. 2
    Servidor (λ = 1/s, T = 60 s).

    ~60 requests para test de carga de un minuto.

  3. 3
    Fallas (λ = 0,1/día, T = 365).

    ~36 fallas al año para plan de repuestos.

  4. 4
    Depuración (λ = 2, T = 5, semilla fija).

    Misma lista siempre: se puede inspeccionar a mano.

  5. 5
    Escala (λT = 10⁶).

    Por esperas es lento: conviene conteo directo Po(λT).

05 · Representación en Python

El simulador en diez líneas

En Python, el simulador es una función simular_poisson(T, lam, semilla) que devuelve arribos. Otra función deriva N(t). La verificación usa muchas réplicas.

Python en tu navegador. Estos bloques se ejecutan localmente con Pyodide, sin instalar nada. Cambiá la semilla y verificá que N(T) cambia pero la media no.

import random, math

def simular_poisson(T, lam=1.0, semilla=7):
    # Acumula esperas Exp(lam) hasta superar T.
    random.seed(semilla)
    t, arribos = 0.0, []
    while True:
        t += -math.log(1 - random.random()) / lam
        if t > T:
            break
        arribos.append(round(t, 2))
    return arribos

a = simular_poisson(10, lam=1.0, semilla=7)
print("N(10) =", len(a))
print(a)

Ejecutá con semilla 7 y 8: distintas listas, mismo proceso. La semilla fija la historia, no el modelo.

Verificar con media y varianza

El test que todo simulador Poisson debe pasar:

import random, math, statistics

def N_T(T, lam=1.0):
    t, n = 0.0, 0
    while True:
        t += -math.log(1 - random.random()) / lam
        if t > T:
            return n
        n += 1

random.seed(3)
datos = [N_T(10) for _ in range(500)]
print("media:", round(statistics.mean(datos), 2))
print("varianza:", round(statistics.pvariance(datos), 2), "| teoría: 10")

06 · Exploración

Laboratorio: generar y verificar Poisson

Generamos R réplicas por esperas Exp(λ) hasta T. Cada escalera es un N(t); la recta punteada es λt. Abajo, el test: media ≈ varianza ≈ λT. Movete λ y T y exigile al generador que cumpla.

EXPERIMENTO 13

Receta por esperas, test por conteos

Sₖ ~ Exp(λ) → N(T) con media ≈ var ≈ λT

Los resultados numéricos aparecen debajo.
Media N(T)0,00
Varianza N(T)0,00
Teoría λT0,00
LecturaGenerador OK

Con λ 1,00 y T 10, media y varianza rondan 10.

Las escaleras se generan espera por espera; el test se lee en los números. Con pocas réplicas el test fluctúa: subí réplicas para estabilizarlo.

Preguntas para explorar

  1. Con 2 réplicas, ¿media y varianza dan 10? ¿Qué le falta al test?
  2. Subí réplicas a 12 con igual λ y T. ¿El test mejora? ¿Por qué?
  3. Triplicá λ con igual T. ¿Las escaleras se empinan al triple? ¿La varianza también?
Ver respuestas sugeridas
  1. No necesariamente: con 2 muestras el ruido manda. Al test le faltan réplicas.
  2. Sí: más muestra, menos ruido. Media y varianza se pegan a λT.
  3. Sí: media y varianza viajan juntas al triple. Sello Poisson.

07 · Comprensión

Confusiones frecuentes

«Sortear N(T) alcanza para la trayectoria»

N(T) da el total, no los instantes. Para la escalera hacen falta esperas (o uniformes ordenados).

«La semilla cambia el modelo»

No: cambia la historia. El modelo es (λ, T, receta); la semilla solo fija qué historia sale.

«Descartar el sorteo que supera T sesga»

No: ese sorteo cae fuera del horizonte y no es un arribo. Incluirlo contaría de más.

«Si media ≈ λT ya está verificado»

Falta la varianza: muchos generadores rotos dan la media pero no la dispersión Poisson.

08 · Práctica guiada

Ejercicios con Python

Ejercicio 1: inspeccionar una réplica

Generá una réplica con semilla fija y calculá esperas, N(5) y N(10). Verificá que N crece.

import random, math

def simular_poisson(T, lam=1.0, semilla=7):
    random.seed(semilla)
    t, arribos = 0.0, []
    while True:
        t += -math.log(1 - random.random()) / lam
        if t > T:
            break
        arribos.append(round(t, 2))
    return arribos

a = simular_poisson(10, semilla=7)
N = lambda t: sum(1 for x in a if x <= t)
print(a)
print("N(5) =", N(5), "| N(10) =", N(10))
Ver solución razonada

Con semilla 7 salen ≈ 8–12 arribos y N(5) ≤ N(10) siempre: la escalera no baja. Cambiá la semilla y repetí.

Ejercicio 2: el test con pocas réplicas

Sin ejecutar primero: con R = 5 y λT = 10, ¿el test será exacto? Comprobalo con R = 5 y R = 1000.

import random, math, statistics

def N_T(T=10, lam=1.0):
    t, n = 0.0, 0
    while True:
        t += -math.log(1 - random.random()) / lam
        if t > T:
            return n
        n += 1

for R in [5, 1000]:
    random.seed(1)
    d = [N_T() for _ in range(R)]
    print(R, round(statistics.mean(d), 2), round(statistics.pvariance(d), 2))
Ver solución

Con R = 5 el test fluctúa (7, 13…); con R = 1000 se pega a 10. El generador necesita muestra para mostrarse.

Ejercicio 3: costo λ·T·R

Estimá cuántos sorteos hace tu simulador con λ = 5, T = 100 y R = 200. ¿Conviene por esperas?

Ver una posible respuesta
print(5 * 100 * 200)

Son 100000 exponenciales: viable. Con λT = 10⁶ por réplica, mejor conteo directo Po(λT) + uniformes.

09 · Síntesis

Ideas para recordar

  • Receta: Sₖ ~ Exp(λ), acumular hasta T, contar.
  • Firma: simular_poisson(T, lam, semilla) → arribos.
  • Test: media ≈ varianza ≈ λT con R grande.
  • Semilla fija depura; semillas variadas estiman.
  • Costo λ·T·R: a gran escala, conteo directo.

En el próximo tema el ritmo dejará de ser parejo: procesos de Poisson no homogéneos.