Reproducibility package: UWCA semantic multiple access (TWC submission)
This commit is contained in:
Executable
+153
@@ -0,0 +1,153 @@
|
||||
"""Generate the five new revision figures from data/*.json into ../Relevance_TWCOM_R2/fig/.
|
||||
Uniform geometry: 8:6 axes box, shared rcParams, no tight bounding box.
|
||||
"""
|
||||
import json
|
||||
from pathlib import Path
|
||||
|
||||
import matplotlib
|
||||
matplotlib.use("Agg")
|
||||
import matplotlib.pyplot as plt
|
||||
import numpy as np
|
||||
|
||||
HERE = Path(__file__).resolve().parent
|
||||
DATA = HERE / "data"
|
||||
FIG = HERE.parent / "Relevance_TWCOM_R2" / "fig"
|
||||
FIG.mkdir(exist_ok=True)
|
||||
|
||||
plt.rcParams.update({
|
||||
"font.size": 9, "axes.labelsize": 10, "axes.titlesize": 10,
|
||||
"legend.fontsize": 7.5, "xtick.labelsize": 8.5, "ytick.labelsize": 8.5,
|
||||
"lines.linewidth": 1.4, "lines.markersize": 4.5,
|
||||
"figure.dpi": 200, "savefig.dpi": 300,
|
||||
"grid.alpha": 0.35, "axes.grid": True,
|
||||
})
|
||||
AXRECT = [0.17, 0.165, 0.79, 0.80] # single panel 8:6-ish
|
||||
FSIZE = (3.5, 2.75)
|
||||
|
||||
|
||||
def newfig():
|
||||
f = plt.figure(figsize=FSIZE)
|
||||
ax = f.add_axes(AXRECT)
|
||||
return f, ax
|
||||
|
||||
|
||||
def save(f, name, axes=None):
|
||||
f.canvas.draw()
|
||||
if axes:
|
||||
for ax in axes:
|
||||
for lbl in [ax.xaxis.label, ax.yaxis.label]:
|
||||
bb = lbl.get_window_extent()
|
||||
fw, fh = f.canvas.get_width_height()
|
||||
assert bb.x0 >= -1 and bb.y0 >= -1 and bb.x1 <= fw + 1 \
|
||||
and bb.y1 <= fh + 1, f"label clipped in {name}"
|
||||
f.savefig(FIG / name)
|
||||
plt.close(f)
|
||||
print("saved", FIG / name)
|
||||
|
||||
|
||||
C = {"ofdma": "#546E7A", "blind": "#8D6E63", "noma": "#E65100",
|
||||
"uwca": "#1565C0", "genie": "#2E7D32", "extra": "#C62828",
|
||||
"aux": "#6A1B9A"}
|
||||
|
||||
# ---------------------------------------------------------------- fig_fair --
|
||||
d = json.load(open(DATA / "e1_fair_baselines.json"))
|
||||
snr = d["snr"]
|
||||
f = plt.figure(figsize=(7.1, 2.75))
|
||||
axs = [f.add_axes([0.115, 0.165, 0.365, 0.77]),
|
||||
f.add_axes([0.615, 0.165, 0.365, 0.77])]
|
||||
for ax, sc, ttl in zip(axs, ["HIGH", "MIX"], ["(a) HIGH", "(b) MIX"]):
|
||||
v = d["scenarios"][sc]
|
||||
ax.semilogy(snr, v["ofdma"]["ser"], "s--", color=C["ofdma"], label="OFDMA")
|
||||
ax.semilogy(snr, v["lmmse_blind"]["ser"], "v-", color=C["blind"],
|
||||
markevery=(1, 2), label="LMMSE-blind")
|
||||
ax.semilogy(snr, v["noma"]["ser"], "^-.", color=C["noma"], label="NOMA-SIC")
|
||||
ax.semilogy(snr, v["uwca"]["ser"], "o-", color=C["uwca"], label="UWCA (prop.)")
|
||||
ax.semilogy(snr, v["lmmse_genie"]["ser"], "d:", color=C["genie"],
|
||||
label="LMMSE-genie")
|
||||
ax.set_xlabel("SNR (dB)")
|
||||
ax.set_ylabel("SER")
|
||||
ax.set_title(ttl)
|
||||
ax.set_xlim(0, 20)
|
||||
axs[1].legend(loc="lower left", framealpha=0.9, fontsize=7)
|
||||
save(f, "fig_fair.pdf", axs)
|
||||
|
||||
# -------------------------------------------------------------- fig_resorth --
|
||||
d = json.load(open(DATA / "e6_residual_orth.json"))
|
||||
snr = d["snr"]
|
||||
f, ax = newfig()
|
||||
ax.plot(snr, d["uwca"]["rho_input"], "k--", label=r"input $\rho(\mathbf{e}_u,\mathbf{e}_v)$")
|
||||
ax.plot(snr, d["uwca"]["rho_decoded"], "o-", color=C["uwca"],
|
||||
label=r"UWCA decoded $\rho(\hat{\mathbf{e}}_u,\hat{\mathbf{e}}_v)$")
|
||||
ax.plot(snr, d["uwca"]["rho_residual"], "s-", color=C["extra"],
|
||||
label=r"UWCA residual $\rho(\mathbf{r}_u,\mathbf{r}_v)$")
|
||||
ax.plot(snr, d["ofdma"]["rho_decoded"], "^:", color=C["ofdma"],
|
||||
label=r"OFDMA decoded")
|
||||
ax.set_xlabel("SNR (dB)")
|
||||
ax.set_ylabel("Pearson correlation")
|
||||
ax.set_xlim(0, 20)
|
||||
ax.set_ylim(-0.05, 0.62)
|
||||
ax.legend(loc="upper right", framealpha=0.9, fontsize=6.8)
|
||||
save(f, "fig_resorth.pdf", [ax])
|
||||
|
||||
# --------------------------------------------------------------- fig_phase2 --
|
||||
d = json.load(open(DATA / "e2_phase_iui.json"))
|
||||
sg = d["sigma_phi_deg"]
|
||||
f, ax = newfig()
|
||||
sty = {"complexI_zerotrain": ("o-", C["uwca"], "mismatch-trained"),
|
||||
"complexI_augtrain": ("s--", C["genie"], "phase-augmented"),
|
||||
"complexIQ_iqtrain": ("^:", C["extra"], "two-rail (I/Q)")}
|
||||
for key, (mk, col, lab) in sty.items():
|
||||
ax.plot(sg, d["curves"][key]["10.0"]["ser"], mk, color=col, label=lab)
|
||||
for key, (mk, col, lab) in sty.items():
|
||||
ax.plot(sg, d["curves"][key]["20.0"]["ser"], mk, color=col, alpha=0.45,
|
||||
label="_nolegend_")
|
||||
ax.annotate("10 dB", xy=(1.5, 0.29), fontsize=8)
|
||||
ax.annotate("20 dB", xy=(1.5, 0.135), fontsize=8)
|
||||
ax.set_xlabel(r"phase residual $\sigma_\varphi$ (deg)")
|
||||
ax.set_ylabel("SER")
|
||||
ax.set_ylim(0.0, 0.45)
|
||||
ax.legend(loc="upper left", framealpha=0.9, fontsize=7)
|
||||
save(f, "fig_phase2.pdf", [ax])
|
||||
|
||||
# ---------------------------------------------------------------- fig_async --
|
||||
d = json.load(open(DATA / "e4_v3_async.json"))
|
||||
dm = d["dmax"]
|
||||
f, ax = newfig()
|
||||
cur = d["curves"]
|
||||
ax.plot(dm, [a[0] for a in cur["uwca_uncorrected"]["10.0"]], "o--",
|
||||
color=C["uwca"], alpha=0.5, label="UWCA, uncorrected")
|
||||
ax.plot(dm, [a[0] for a in cur["ofdma_uncorrected"]["10.0"]], "s--",
|
||||
color=C["ofdma"], alpha=0.5, label="OFDMA, uncorrected")
|
||||
ax.plot(dm, [a[0] for a in cur["uwca_corrected"]["10.0"]], "o-",
|
||||
color=C["uwca"], label="UWCA, realigned")
|
||||
ax.plot(dm, [a[0] for a in cur["ofdma_corrected"]["10.0"]], "s-",
|
||||
color=C["ofdma"], label="OFDMA, realigned")
|
||||
ax.plot(dm, [a[0] for a in cur["uwca_corrected_err20"]["10.0"]], "^-.",
|
||||
color=C["extra"], label="UWCA, realigned (20% est. err.)")
|
||||
ax.set_xlabel(r"maximum timing offset $\Delta$ (symbols)")
|
||||
ax.set_ylabel("SER")
|
||||
ax.set_ylim(0, 1.05)
|
||||
ax.legend(loc="lower right", ncol=2, framealpha=0.9, fontsize=6.0)
|
||||
save(f, "fig_async.pdf", [ax])
|
||||
|
||||
# ------------------------------------------------------------- fig_dynusers --
|
||||
d = json.load(open(DATA / "e3_dynamic_users.json"))
|
||||
ks = d["k"]
|
||||
f = plt.figure(figsize=FSIZE)
|
||||
ax = f.add_axes([0.20, 0.165, 0.76, 0.80])
|
||||
ax.plot(ks, [a[1] for a in d["fixed8"]["10.0"]], "o-", color=C["uwca"],
|
||||
label="single model, 10 dB")
|
||||
ax.plot(ks, [a[1] for a in d["fixed8"]["20.0"]], "o--", color=C["uwca"],
|
||||
alpha=0.5, label="single model, 20 dB")
|
||||
ok = sorted(int(k) for k in d["oracle"])
|
||||
ax.plot(ok, [d["oracle"][str(k)]["10.0"][1] for k in ok], "s", ls="none",
|
||||
color=C["extra"], label="per-count retrained, 10 dB")
|
||||
ax.plot(ok, [d["oracle"][str(k)]["20.0"][1] for k in ok], "s", ls="none",
|
||||
mfc="none", color=C["extra"], label="per-count retrained, 20 dB")
|
||||
ax.set_xlabel(r"number of active users $|\mathcal{A}|$")
|
||||
ax.set_ylabel(r"mean cosine $\bar{c}$")
|
||||
ax.set_ylim(0.28, 0.47)
|
||||
ax.legend(loc="upper left", framealpha=0.9, fontsize=6.8)
|
||||
save(f, "fig_dynusers.pdf", [ax])
|
||||
|
||||
print("ALL FIGURES DONE")
|
||||
Reference in New Issue
Block a user