Intermedio · Juego del caos

Lección 4: Bucles que recuerdan

Construye en Python el patrón «Juego del caos» y aprende por el camino:

  • un bucle que lleva su estado de un paso al siguiente
  • números enteros aleatorios con rng.integers
  • un bucle while para una condición
  • arrays de puntos y slicing
  • np.column_stack

Míralo primero

Se reproduce desde YouTube tras hacer clic.

chaos-game.py
"""Chaos game: jump a part r of the way to a random corner of a polygon, again and again.
Run: python chaos-game.py   (needs: pip install numpy matplotlib)
"""
import numpy as np
import matplotlib.pyplot as plt

plt.style.use("dark_background")

corners, r, no_repeat = 3, 0.5, False  # triangle, halfway: the Sierpinski triangle
steps = 60000
rng = np.random.default_rng()

angles = np.pi / 2 + 2 * np.pi * np.arange(corners) / corners
vertex = np.column_stack([np.cos(angles), np.sin(angles)])

points, chosen = np.zeros((steps, 2)), np.zeros(steps, dtype=int)
x, last = np.array([0.0, 0.0]), -1
for i in range(steps):
    c = rng.integers(corners)
    while no_repeat and c == last:  # the restricted game: never the same corner twice
        c = rng.integers(corners)
    x = x + r * (vertex[c] - x)  # the whole rule
    points[i], chosen[i], last = x, c, c

plt.figure(figsize=(6, 6))
plt.scatter(points[20:, 0], points[20:, 1], s=0.3, c=chosen[20:], cmap="rainbow")
plt.axis("equal")
plt.axis("off")
plt.show()

# Try: corners, r = 5, 0.618 (a pentagon) or corners, no_repeat = 4, True (a square, restricted)

¿No tienes Python en este equipo? El cuaderno ejecuta el mismo script, los ejercicios y las respuestas en tu navegador, en Google Colab. El cuaderno está en inglés.

Línea a línea

  1. vertex = np.column_stack([np.cos(angles), np.sin(angles)])

    Los vértices del polígono: sus valores x e y uno al lado del otro, una fila por vértice.

  2. c = rng.integers(corners)

    Un número entero aleatorio de 0 a corners − 1: el vértice hacia el que saltar.

  3. while no_repeat and c == last:

    El juego con restricción: mientras el nuevo vértice sea el último, vuelve a sortear.

  4. x = x + r * (vertex[c] - x)

    La regla: avanza la parte r del camino del punto al vértice. Con r = 0.5, hasta la mitad.

  5. points[i], chosen[i], last = x, c, c

    Guarda el punto y su vértice, y recuerda el vértice para el paso siguiente.

  6. plt.scatter(points[20:, 0], points[20:, 1], s=0.3, c=chosen[20:], cmap="rainbow")

    Sáltate los 20 primeros puntos, que aún van de camino al fractal, y colorea el resto según su vértice.

Pruébalo tú

  1. Dibuja un pentágono cuyas cinco copias apenas se toquen.

    Pista

    Cambia corners y r en una sola línea.

    Respuesta

    corners, r, no_repeat = 5, 0.618, False

  2. ¿Por qué el gráfico se salta los 20 primeros puntos?

    Pista

    ¿Dónde empieza el punto?

    Respuesta

    Empieza en el centro, que no está en el fractal. Cada salto reduce a la mitad su distancia al fractal, así que tras 20 saltos está a menos de una millonésima (2⁻²⁰) del tamaño de la imagen.

  3. Juega al juego del cuadrado con no_repeat y sin él. ¿Qué cambia?

    Pista

    corners = 4, r = 0.5.

    Respuesta

    Sin la restricción, los puntos simplemente llenan el cuadrado; con no_repeat = True aparece un fractal.

Cuestionario

1. ¿Qué puede devolver rng.integers(3)?
2. ¿Qué es x + 0.5 * (corner - x)?
3. ¿Por qué el bucle guarda la variable last?
4. ¿Qué selecciona points[20:, 0]?
5. ¿Por qué un orden aleatorio dibuja aun así una imagen precisa?

Tarjetas de repaso

Lee el anverso, di el reverso para ti y luego abre la tarjeta.

  • rng.integers(n)

    Un número entero aleatorio de 0 a n − 1.

  • while condition:

    Repite su bloque mientras la condición sea True.

  • a[20:, 0]

    Las filas de la 20 al final, columna 0, de un array 2D.

  • Contracción

    Un paso que acerca entre sí dos puntos cualesquiera, como un salto a medio camino hacia un vértice.

  • Atractor

    La forma sobre la que los pasos repetidos atraen a todos los puntos: aquí, el triángulo de Sierpiński.

Estas tarjetas en su propia página →