"""F4-conf-02: verdicts on six assertions against their cited source extracts. Reads only data/; writes out/results.json deterministically. No randomness.""" import json, math, os, re ROOT = os.path.dirname(os.path.dirname(os.path.abspath(__file__))) D = os.path.join(ROOT, "data") DCR = "arxiv-2609.27732v1" RES = "arxiv-2606.14621v1" def lines(p): with open(p, encoding="utf-8") as f: return f.read().split("\n") src = {DCR: lines(os.path.join(D, "sources", DCR + ".txt")), RES: lines(os.path.join(D, "sources", RES + ".txt"))} with open(os.path.join(D, "assertions.json"), encoding="utf-8") as f: assertions = json.load(f) A = {a["id"]: a for a in assertions} for a in assertions: assert a["cites"] in src, a def wcl(p): with open(p, "rb") as f: return f.read().count(b"\n") n_input_rows = { "assertions.json": len(assertions), "README.md": wcl(os.path.join(D, "README.md")), DCR + ".txt": wcl(os.path.join(D, "sources", DCR + ".txt")), RES + ".txt": wcl(os.path.join(D, "sources", RES + ".txt")), } def find(sid, pattern, start=0): """Return (index, line) of first line at/after start matching regex; print it.""" for i in range(start, len(src[sid])): if re.search(pattern, src[sid][i]): print(f" [{sid} L{i+1}] {src[sid][i].strip()}") return i, src[sid][i] raise ValueError(f"pattern not found: {pattern}") def cells(line): return [c.strip() for c in line.split("|")] def num(s): return float(re.sub(r"[^0-9.\-]", "", s.replace("−", "-"))) def pct(b): return 100.0 * (math.exp(b) - 1.0) def ci(b, se, z): return (b - z * se, b + z * se) def stars(s): return len(re.findall(r"\*", s)) verdicts, locators, reasons, data_issues = {}, {}, {}, [] cols = {"1 km": 1, "3 km": 2, "5 km": 3} # ---------------- Table 6 (DCR) ---------------- print("Table 6 lines relied on:") i6, _ = find(DCR, r"^Table 6:") iatt, latt = find(DCR, r"^ATT \|", i6) _, lse = find(DCR, r"^\| \(", iatt) _, lpct = find(DCR, r"^% change \|", iatt) t6 = {k: {"att_s": cells(latt)[v], "att": num(cells(latt)[v]), "se": num(cells(lse)[v]), "pct": num(cells(lpct)[v])} for k, v in cols.items()} find(DCR, r"statistically significant at the 5% level", i6) # A1 print("A1:", A["A1"]["text"]) r = t6["5 km"] z = r["att"] / r["se"] lo, hi = ci(r["att"], r["se"], 1.96) ok = (r["att"] == -0.431 and r["se"] == 0.210 and stars(r["att_s"]) >= 2 and abs(z) > 1.96 and r["pct"] == -35.0 and round(pct(r["att"]), 1) == -35.0) print(f" check: ATT={r['att']} SE={r['se']} stars={stars(r['att_s'])} |z|={abs(z):.3f} " f"CI95=[{lo:.3f},{hi:.3f}] printed%={r['pct']} 100(exp(b)-1)={pct(r['att']):.2f}") verdicts["A1"] = "supported" if ok else "not_supported" locators["A1"] = f'{DCR} | Table 6 | row "ATT" | column "5 km"' reasons["A1"] = ("Table 6 prints the 5 km ATT as -0.431** (SE 0.210, ** = p<0.05) with a % change of -35.0% " "(100*(exp(-0.431)-1) = -35.0%), matching every element of the assertion.") # A3 print("A3:", A["A3"]["text"]) r = t6["3 km"] print(f" check: ATT={r['att']} printed%={r['pct']} 100(exp(b)-1)={pct(r['att']):.2f} vs asserted -28.3%") ok = r["att"] == -0.283 and abs(pct(r["att"]) - (-28.3)) < 0.05 verdicts["A3"] = "supported" if ok else "not_supported" locators["A3"] = f'{DCR} | Table 6 | row "% change" | column "3 km"' reasons["A3"] = ("The ATT of -0.283 is in log points and Table 6 converts it to a -24.7% change " f"(100*(exp(-0.283)-1) = {pct(r['att']):.2f}%), not a 28.3% reduction; the estimate is also not " "significant (SE 0.279).") # ---------------- Table 7 (DCR) ---------------- print("Table 7 lines relied on:") i7, _ = find(DCR, r"^Table 7:") def t7row(label): i, l = find(DCR, r"^" + re.escape(label) + r" \|", i7) _, s = find(DCR, r"^\| \(", i) return {k: {"att_s": cells(l)[v], "att": num(cells(l)[v]), "se": num(cells(s)[v])} for k, v in cols.items()} hiv = t7row("HIV") hep = t7row("Hepatitis") find(DCR, r"HIV estimates are insignificant and close to zero", i7) # A2 print("A2:", A["A2"]["text"]) r = hiv["1 km"] print(f" check: HIV 1 km ATT={r['att_s']} (SE {r['se']}); asserted -0.063") verdicts["A2"] = "supported" if r["att"] < 0 else "not_supported" locators["A2"] = f'{DCR} | Table 7 | row "HIV" | column "1 km"' reasons["A2"] = ("Table 7 prints the 1 km HIV ATT as 0.063, i.e. positive (SE 0.801), so the asserted negative sign " "and the claimed fall in HIV hospitalisations are contradicted.") # A4 print("A4:", A["A4"]["text"]) r = hep["5 km"] c196 = ci(r["att"], r["se"], 1.96); c2 = ci(r["att"], r["se"], 2.0) c1 = ci(r["att"], r["se"], 1.0); c1645 = ci(r["att"], r["se"], 1.645) print(f" check: Hepatitis 5 km ATT={r['att_s']} SE={r['se']} CI95(1.96)=[{c196[0]:.3f},{c196[1]:.3f}] " f"CI95(2.0)=[{c2[0]:.3f},{c2[1]:.3f}] CI90=[{c1645[0]:.3f},{c1645[1]:.3f}] b±1SE=[{c1[0]:.3f},{c1[1]:.3f}]") excl = c196[1] < 0 or c196[0] > 0 verdicts["A4"] = "supported" if excl else "not_supported" locators["A4"] = f'{DCR} | Table 7 | row "Hepatitis" | column "5 km"' reasons["A4"] = (f"With ATT -0.406 and SE 0.250 (no stars), the 95% CI is about [{c196[0]:.2f}, {c196[1]:.2f}], " "which includes zero; the asserted [-0.66, -0.16] is only the estimate ± 1 SE.") # A5 print("A5:", A["A5"]["text"]) hits = [i + 1 for i, l in enumerate(src[DCR]) if re.search(r"\b(men|women|male|female|sex|gender)\b", l, re.I)] print(f" check: lines mentioning men/women/male/female/sex/gender in {DCR}: {hits}") verdicts["A5"] = "not_assessable" if not hits else "MANUAL_REVIEW" locators["A5"] = f"not reported in {DCR}" reasons["A5"] = ("The extract reports no estimates by sex (Tables 6, 7 and A19 report only buffer, outcome-category and estimator breakdowns, none by sex), " "so a men-versus-women comparison can be neither confirmed nor refuted.") # ---------------- RESEA Table 2 ---------------- print("A6:", A["A6"]["text"]) _, l = find(RES, r"^Weeks on UI \|") c = cells(l) ctrl = num(re.match(r"([\d.]+) weeks", c[2]).group(1)) m = re.match(r"(-?[\d.]+) weeks; p<0\.001; 95% CI: \[(-?[\d.]+), (-?[\d.]+)\]", c[4]) ate, lo6, hi6 = (float(m.group(k)) for k in (1, 2, 3)) find(RES, r"11\.5% decrease") rel = 100 * ate / ctrl print(f" check: ATE={ate} CI=[{lo6},{hi6}] control mean={ctrl} ATE/control={rel:.2f}%") ok = ate == -1.99 and (lo6, hi6) == (-2.24, -1.75) and ctrl == 17.3 and round(rel, 1) == -11.5 verdicts["A6"] = "supported" if ok else "not_supported" locators["A6"] = f'{RES} | Table 2 | row "Weeks on UI" | column "Average treatment effect estimate"' reasons["A6"] = ("Table 2 prints the ATE for weeks on UI as -1.99 weeks (95% CI [-2.24, -1.75]) with a control mean " f"of 17.3 weeks, and -1.99/17.3 = {rel:.1f}%, matching the text's 11.5% decrease.") # ---------------- internal-consistency scan (data issues) ---------------- print("Consistency checks on DCR extract:") iA19, _ = find(DCR, r"^Table A19:") ia, la = find(DCR, r"^ATT \|", iA19) _, lsa = find(DCR, r"^\| \(", ia) _, lpa = find(DCR, r"^% change \|", ia) find(DCR, r"never-treated comparison regions \(640 regions\)", iA19) se_a19 = num(cells(lsa)[1]) data_issues.append({ "issue": (f"{DCR}: the CS-DR 5 km overall ATT -0.431** has SE 0.210 in Table 6 but SE {se_a19:.3f} in Appendix " "Table A19 (same estimator, buffer, window and N=17,250)."), "handling": ("A1 is judged on Table 6 (the cited main result); the 5% significance claim holds under both SEs " f"(|z| = {0.431/0.210:.2f} and {0.431/se_a19:.2f} > 1.96), so the verdict is unaffected.")}) data_issues.append({ "issue": f"{DCR}: Table A19 lists 608 control regions but its note says 640 never-treated comparison regions.", "handling": "Not decisive for any assertion; recorded only."}) fatal5 = num(cells(find(DCR, r"^Drug-related \(fatal\) \|", i7)[1])[3]) data_issues.append({ "issue": (f"{DCR}: the abstract says fatal outcomes fall by 35%, whereas Table 7 gives a 5 km fatal ATT of " f"{fatal5} (100*(exp(b)-1) = {pct(fatal5):.1f}%) and Section 6.1 says approximately 30%."), "handling": "Not decisive for any assertion (none concerns fatal outcomes); recorded only."}) for k, lab in [(3, "Synthetic DiD"), (4, "Stacked DiD")]: b = num(cells(la)[k]); p = num(cells(lpa)[k]) print(f" A19 {lab}: b={b} printed%={p} computed={pct(b):.2f}") data_issues.append({ "issue": (f"{DCR}: Table A19 printed % changes for Synthetic DiD ({num(cells(lpa)[3])}%) and Stacked DiD " f"({num(cells(lpa)[4])}%) differ by 0.1 pp from 100*(exp(b)-1) " f"({pct(num(cells(la)[3])):.1f}%, {pct(num(cells(la)[4])):.1f}%), likely rounding from unrounded b."), "handling": "Not decisive for any assertion; recorded only."}) data_issues.append({ "issue": (f"{RES}: the results text reports the weeks-on-UI CI as magnitudes ([1.75 weeks, 2.24 weeks]) while " "Table 2 prints signed bounds [-2.24, -1.75]; the text also contains a rendering defect 'p ¡ 0.001'."), "handling": "Treated as equivalent sign conventions; A6 judged on the signed Table 2 values."}) # ---------------- naive baseline: share of asserted numbers found verbatim in the cited extract ---------------- baseline = {} for a in assertions: toks = re.findall(r"\d+(?:\.\d+)?", a["text"].replace("−", "-")) text = "\n".join(src[a["cites"]]) found = sum(1 for t in toks if t in text) baseline[a["id"]] = round(found / len(toks), 4) if toks else None print("Baseline (share of asserted numeric tokens found verbatim in cited extract):", baseline) verdicts = {k: verdicts[k] for k in sorted(verdicts)} locators = {k: locators[k] for k in sorted(locators)} reasons = {k: reasons[k] for k in sorted(reasons)} counts = {v: sum(1 for x in verdicts.values() if x == v) for v in ("supported", "not_supported", "not_assessable")} results = { "task_id": "F4-conf-02", "verdicts": verdicts, "locators": locators, "reasons": reasons, "n_supported": counts["supported"], "n_not_supported": counts["not_supported"], "n_not_assessable": counts["not_assessable"], "feasibility": "complete", "feasibility_reason": None, "data_issues": data_issues, "n_input_rows": n_input_rows, "n_analysed": len(verdicts), "random_seed": None, "baseline_share_numbers_found_verbatim": baseline, } assert sum(counts.values()) == 6 os.makedirs(os.path.join(ROOT, "out"), exist_ok=True) with open(os.path.join(ROOT, "out", "results.json"), "w", encoding="utf-8") as f: json.dump(results, f, indent=2, ensure_ascii=False) f.write("\n") print("Verdicts:", verdicts) print("Counts:", counts)