“datashader”, “colorcet”, “numba”, “scipy”]) importar numpy como np importar pandas como pd importar datashader como ds importar datashader.transfer_functions como tf desde datashader importar reducciones como rd importar colorcet como cc importar matplotlib.pyplot como plt importar matplotlib.colors como mcolors desde matplotlib.gridspec importar GridSpec desde scipy.stats importar multivariate_normal tiempo de importación, advertencias advertencias.filterwarnings(“ignore”) print(“Versión de Datashader:”, ds.__version__) def show(img, title=””, ax=None, figsize=(6, 5)): standalone = ax es Ninguno si es independiente: fig, ax = plt.subplots(figsize=figsize) rgba = img.to_pil() ax.imshow(rgba, origin=”upper”, aspecto=”auto”) ax.set_title(title, fontsize=11, fontweight=”bold”) ax.axis(“off”) si es independiente: plt.tight_layout() plt.show() print(“\n=== SECCIÓN 1: Core Pipeline ===”) rng = np.random.default_rng(42) N = 2_000_000 x = np.concatenate([rng.normal(-1, 0.5, N//3),
rng.normal( 1, 0.5, N//3),
rng.normal( 0, 1.5, N//3)]) y = np.concatenar([rng.normal(-1, 0.5, N//3),
rng.normal( 1, 0.5, N//3),
rng.normal( 0, 0.5, N//3)]) df_base = pd.DataFrame({“x”: x, “y”: y}) lienzo = ds.Canvas(plot_width=600, plot_height=500, x_range=(-4, 4), y_range=(-4, 4)) agg = canvas.points(df_base, “x”, “y”, agg=rd.count()) fig, ejes = plt.subplots(1, 3, tamaño de figura=(15, 4)) combos = [
(“Linear / blues”, tf.shade(agg, cmap=cc.blues, how=”linear”)),
(“Log / fire”, tf.shade(agg, cmap=cc.fire, how=”log” )),
(“Eq-hist / bmy”, tf.shade(agg, cmap=cc.bmy, how=”eq_hist”)),
]
para ax, (title, img) en zip(axes, combos): show(img, title, ax=ax) plt.suptitle(“Sección 1 – 2 M puntos: normalización lineal vs Log vs Eq-Hist”, fontsize=13, fontweight=”bold”) plt.tight_layout() plt.show() print(“\n=== SECCIÓN 2: Tipos de reducción ===”) n_actual = len(df_base) df_base[“value”] = rng.exponencial(escala=2, tamaño=n_actual) df_base[“label”] = pd.Categorical( rng.elección([“A”, “B”, “C”]tamaño=n_actual), categorías=[“A”, “B”, “C”]
) lienzo2 = ds.Canvas(ancho_trama=400, altura_trama=350, rango_x=(-4, 4), rango_y=(-4, 4)) cfg_reducciones = [
(“count()”, rd.count(), cc.kbc),
(“sum(value)”, rd.sum(“value”), cc.CET_L3),
(“mean(value)”, rd.mean(“value”), cc.CET_D4),
(“std(value)”, rd.std(“value”), cc.CET_L16),
(“min(value)”, rd.min(“value”), cc.CET_L17),
(“max(value)”, rd.max(“value”), cc.bgyw),
(“var(value)”, rd.var(“value”), cc.CET_L18),
(“count_cat(label)”, rd.count_cat(“label”), None),
]
fig, axes = plt.subplots(2, 4, figsize=(18, 9)) axes = axes.flat para ax, (nombre, agg_fn, cmap) en zip(axes, reducciones_cfg): agg_r = canvas2.points(df_base, “x”, “y”, agg=agg_fn) si cmap es Ninguno: img = tf.shade(agg_r, color_key={“A”:”#e41a1c”,”B”:”#377eb8″,”C”:”#4daf4a”}) else: img = tf.shade(agg_r, cmap=cmap, how=”eq_hist”) show(img, name, ax=ax) plt.suptitle(“Sección 2 – Todos los tipos de reducción en 2 M puntos”, fontsize=14, fontweight=”bold”) plt.tight_layout() plt.show() print(“\n=== SECCIÓN 3: Visualización categórica ===”) N_cat = 500_000 categorías = [“Cluster A”, “Cluster B”, “Cluster C”, “Cluster D”]
centros = [(-2, -2), (-2, 2), (2, -2), (2, 2)]
colores = {“Grupo A”:”#e41a1c”,”Grupo B”:”#377eb8″, “Grupo C”:”#4daf4a”,”Grupo D”:”#ff7f00″} cuadros = []
para cat, (cx, cy) en zip(categorías, centros): n = N_cat // len(categorías) frames.append(pd.DataFrame({ “x”: rng.normal(cx, 0.8, n), “y”: rng.normal(cy, 0.8, n), “cat”: pd.Categorical([cat]*n, categorías=categorías), })) df_cat = pd.concat(frames, ignore_index=True) canvas3 = ds.Canvas(plot_width=500, plot_height=500, x_range=(-5, 5), y_range=(-5, 5)) agg_cat = canvas3.points(df_cat, “x”, “y”, agg=rd.count_cat(“cat”)) fig, axes = plt.subplots(1, 3, figsize=(16, 5)) img_raw = tf.shade(agg_cat, color_key=colors) show(img_raw, “Raw (sin extensión)”, ax=axes[0]) img_sp1 = tf.spread(tf.shade(agg_cat, color_key=colores), px=1) show(img_sp1, “Difundir px=1″, ax=ejes[1]) img_bg = tf.set_background(tf.shade(agg_cat, color_key=colores), color=”negro”) show(img_bg, “Fondo negro”, ax=ejes[2]) para gato, col en colores.items(): ejes[2].trama([], []”o”, color=col, etiqueta=cat, tamaño de marcador=8) ejes[2].legend(loc=”abajo a la derecha”, fontsize=8, framealpha=0.6) plt.suptitle(“Sección 3 – Representación categórica (500 k puntos)”, fontsize=13, fontweight=”bold”) plt.tight_layout() plt.show()