46
This commit is contained in:
@@ -1,10 +1,11 @@
|
||||
"""Build vector figure sources, comparison tables, source listings, and a support ZIP.
|
||||
"""Build vector figure sources, comparison tables, the formal-data table, and a support ZIP.
|
||||
|
||||
Formal figures use the audited snapshot only. Geometric figures use declared
|
||||
algorithm parameters, not fabricated observations or hidden simulator data.
|
||||
The paired optimal-versus-baseline tables are generated from project/results/*.json
|
||||
so that no number in the comparison section is hand copied.
|
||||
The generated table rows are f-strings whose value equals the LaTeX line to be
|
||||
written; wrapping them would obscure that one-to-one correspondence, so this module
|
||||
is exempt from the line-length check (the only pylint exception in scripts/).
|
||||
"""
|
||||
# pylint: disable=line-too-long
|
||||
|
||||
from __future__ import annotations
|
||||
|
||||
import argparse
|
||||
@@ -18,29 +19,6 @@ ROOT = Path(__file__).resolve().parents[1]
|
||||
PAPER = ROOT / "docs/paper"
|
||||
PROJECT_RESULTS = ROOT / "project/results"
|
||||
|
||||
# Display copies only: executable Python files remain byte-for-byte unchanged.
|
||||
ESCAPE_OPEN = "(" + "*@"
|
||||
ESCAPE_CLOSE = "@*" + ")"
|
||||
LATEX_SYMBOLS = {
|
||||
"\u03b1": r"\alpha", "\u03b4": r"\delta", "\u03b8": r"\theta",
|
||||
"\u03bb": r"\lambda", "\u03c0": r"\pi", "\u03c1": r"\rho",
|
||||
"\u03c6": r"\varphi", "\u2308": r"\lceil", "\u2309": r"\rceil",
|
||||
"\u2200": r"\forall", "\u2203": r"\exists", "\u2205": r"\varnothing",
|
||||
"\u2208": r"\in", "\u2227": r"\wedge", "\u2229": r"\cap",
|
||||
"\u222a": r"\cup", "\u2248": r"\approx", "\u2264": r"\le",
|
||||
"\u2265": r"\ge", "\u2286": r"\subseteq", "\u2287": r"\supseteq",
|
||||
"\u27f9": r"\Longrightarrow",
|
||||
}
|
||||
|
||||
|
||||
def escaped_listing(source: str) -> str:
|
||||
if ESCAPE_OPEN in source or ESCAPE_CLOSE in source:
|
||||
raise ValueError("Source collides with the LaTeX escape delimiters")
|
||||
return "".join(
|
||||
ESCAPE_OPEN + r"\ensuremath{" + LATEX_SYMBOLS[c] + "}" + ESCAPE_CLOSE
|
||||
if c in LATEX_SYMBOLS else c for c in source
|
||||
)
|
||||
|
||||
|
||||
def digest(data: bytes) -> str:
|
||||
return hashlib.sha256(data).hexdigest()
|
||||
@@ -49,7 +27,6 @@ def digest(data: bytes) -> str:
|
||||
def figures(rows: list[dict]) -> None:
|
||||
out = PAPER / "figures"
|
||||
out.mkdir(parents=True, exist_ok=True)
|
||||
<<<<<<< HEAD
|
||||
plan = json.loads((ROOT / "src/mcm26b/guarantee/plans/q4_mincover_v2.json").read_text("utf-8"))
|
||||
lines = [
|
||||
r"\begin{figure}[htbp]\centering",
|
||||
@@ -72,8 +49,6 @@ def figures(rows: list[dict]) -> None:
|
||||
r"\label{fig:q4plan}\end{figure}",
|
||||
]
|
||||
(out / "q4-plan.tex").write_text("\n".join(lines) + "\n", "utf-8")
|
||||
=======
|
||||
>>>>>>> 78e4420a3e496c43db8e06556e539fd7d2aaf231
|
||||
colors = ["inkblue", "inkblue!50", "warmgray!70", "black!18"]
|
||||
bars = [
|
||||
r"\begin{figure}[htbp]\centering",
|
||||
@@ -266,27 +241,12 @@ def project_tables() -> None:
|
||||
|
||||
|
||||
def listings(rows: list[dict]) -> None:
|
||||
"""生成正式数据清单;核心函数源码清单由 build_code_appendix.py 单独生成。
|
||||
|
||||
论文附录只收录四问主线的核心函数(数据源为单文件核心代码 ipynb),
|
||||
评测机、命令行外壳、采集/绘图脚本、测试与未采用方案不再逐字排版。
|
||||
"""
|
||||
data = PAPER / "data"
|
||||
files = sorted((ROOT / "src/mcm26b").rglob("*.py"))
|
||||
files += [ROOT / "scripts/audit_paper_formal.py",
|
||||
ROOT / "scripts/build_paper_support.py"]
|
||||
text = [
|
||||
r"\begingroup",
|
||||
r"\linespread{1.0}\selectfont",
|
||||
r"\lstset{basicstyle=\ttfamily\fontsize{8}{10}\selectfont,numberstyle=\tiny,"
|
||||
r"aboveskip=6pt,belowskip=8pt,xleftmargin=1.5em,frame=none}",
|
||||
]
|
||||
for path in files:
|
||||
rel = path.relative_to(ROOT).as_posix()
|
||||
display = data / "listing-source" / (rel + ".tex")
|
||||
display.parent.mkdir(parents=True, exist_ok=True)
|
||||
display.write_text(escaped_listing(path.read_text("utf-8")), "utf-8")
|
||||
display_rel = display.relative_to(PAPER).as_posix()
|
||||
escape_option = "escapeinside={" + ESCAPE_OPEN + "}{" + ESCAPE_CLOSE + "}"
|
||||
text += [fr"\subsection*{{\pathtext{{{rel}}}}}",
|
||||
fr"\lstinputlisting[{escape_option}]{{{display_rel}}}"]
|
||||
text.append(r"\endgroup")
|
||||
(data / "source-listings.tex").write_text("\n".join(text) + "\n", "utf-8")
|
||||
table = [
|
||||
r"\begin{longtable}{p{1.15cm}p{13.3cm}}",
|
||||
r"\caption{所选正式导出文件与完整包哈希}\label{tab:packages}\\",
|
||||
@@ -356,7 +316,9 @@ def package(rows: list[dict]) -> Path:
|
||||
if path.is_file() and "__pycache__" not in path.parts)
|
||||
selected.update([PAPER / "main.tex", PAPER / "mcm26b-paper.cls",
|
||||
PAPER / "README.md", PAPER / "REWRITE_NOTES.md",
|
||||
ROOT / "mcm26b-核心代码.ipynb",
|
||||
ROOT / "scripts/audit_paper_formal.py",
|
||||
ROOT / "scripts/build_code_appendix.py",
|
||||
ROOT / "scripts/build_paper_support.py"])
|
||||
for row in rows:
|
||||
path = ROOT / "Jammers-simulator-full" / row["file"]
|
||||
|
||||
Reference in New Issue
Block a user