make_f13_C_figure.py — src/6-fourier

The script src/6-fourier/make_f13_C_figure.py of the validation package of the paper 6-four, rendered with an anchor per line. ▶ run the predicates on Google Colab.

6-fourier ledgersrc/6-fourier/make_f13_C_figure.py · 3.3 KBmake_f13_C_figure.pyColab
1"""Framed complex plane figure for F_13(3;0,1,2) — verification rendering.23Canonical frame datum (FRC formalism, cf. the RH paper):4    frame (t;0,1,g_t),  i_t := -g_t^t = g_t^{-t},  e_t := g_t^{i_t}.5Orientation convention: imaginary axis up from the unit 1, phase rotation6g_t^m advancing clockwise.7At p=13, g_t=2:  i_t = -8 = 5,  e_t = 2^5 = 6,  pi_t = 6.89Axis labels: horizontal (f-reals) a <-> a mod p; vertical k*i <-> k*i_t mod p.10Output: f13-C-check.png (cross-check against the manuscript figure11f13-C-20260530.png, which is the canonical rendering).12"""1314import math15import matplotlib1617matplotlib.use("Agg")18import matplotlib.pyplot as plt1920P = 1321G = 222T = (P - 1) // 423I_T = (-pow(G, T, P)) % P  # oriented quarter-turn -g^t: 524assert (I_T * I_T) % P == P - 12526LIM = 5.8527R_MAX = 6.62829BLUE = "#1f77b4"30RED = "#d62728"31PURPLE = "#9467bd"32GREEN = "#2ca02c"33GRAY = "#888888"3435fig, ax = plt.subplots(figsize=(7.1, 7.1), dpi=100)36ax.set_aspect("equal")37ax.axis("off")38ax.set_xlim(-LIM, LIM)39ax.set_ylim(-LIM, LIM)4041# --- concentric circles through the lattice radii ---42radii = sorted({a * a + b * b for a in range(0, 7) for b in range(0, 7)43                if 0 < a * a + b * b <= R_MAX * R_MAX})44green_r2 = {2: 0.9, 5: 0.55, 8: 0.35}  # diagonal/near norm circles, graded45for r2 in radii:46    r = math.sqrt(r2)47    if r2 in green_r2:48        c = plt.Circle((0, 0), r, fill=False, color=GREEN,49                       alpha=green_r2[r2], lw=0.9, zorder=1)50    else:51        c = plt.Circle((0, 0), r, fill=False, color=GRAY,52                       alpha=0.18, lw=0.8, zorder=1)53    ax.add_patch(c)5455# --- lattice points off the axes ---56for a in range(-6, 7):57    for b in range(-6, 7):58        if a == 0 or b == 0:59            continue60        if a * a + b * b <= R_MAX * R_MAX:61            ax.plot(a, b, ".", color=GRAY, ms=4.5, alpha=0.75, zorder=2)6263# --- axes ---64ax.plot([-LIM, LIM], [0, 0], color=BLUE, lw=1.4, zorder=3)65ax.plot([0, 0], [-LIM, LIM], color=RED, lw=1.4, zorder=3)6667# --- horizontal labels: black integers above, purple residues below ---68for a in range(-5, 6):69    if a == 0:70        continue71    ax.annotate(f"{a}", (a, 0), xytext=(0, 7), textcoords="offset points",72                ha="center", va="bottom", fontsize=13, color="black", zorder=4)73    ax.annotate(f"{a % P}", (a, 0), xytext=(0, -7), textcoords="offset points",74                ha="center", va="top", fontsize=12, color=PURPLE, zorder=4)75    ax.plot(a, 0, ".", color=BLUE, ms=4.5, zorder=4)7677# --- vertical labels: red k*i left, purple residues right ---78for b in range(-5, 6):79    if b == 0:80        continue81    ax.annotate(f"{b}i", (0, b), xytext=(-7, 0), textcoords="offset points",82                ha="right", va="center", fontsize=13, color=RED, zorder=4)83    ax.annotate(f"{(b * I_T) % P}", (0, b), xytext=(7, 0),84                textcoords="offset points",85                ha="left", va="center", fontsize=12, color=PURPLE, zorder=4)86    ax.plot(0, b, ".", color=RED, ms=4.5, zorder=4)8788# --- origin ---89ax.annotate("0", (0, 0), xytext=(-6, 6), textcoords="offset points",90            ha="right", va="bottom", fontsize=13, color=BLUE, zorder=5)91ax.plot(0, 0, "o", color=BLUE, ms=5.5, zorder=5)9293fig.savefig("f13-C-check.png", bbox_inches="tight", facecolor="white")94print(f"i_t = {I_T}; labels:",95      {f"{b}i": (b * I_T) % P for b in range(-5, 6) if b})96