SPB Git

spb/wp45_uqo

Public
1.7 KB · 25 lines python
1#!/usr/bin/env python32"""Freeze document-level splits (heldout_v1): 20% held out, stratified by year × article_type, seed 45.3Held-out documents never feed profile construction or prompt tuning. Author-surname overlap between splits is measured and reported."""4import json, random, re, sys5import pandas as pd6sys.path.insert(0, "src")7from jof250 import config8from jof250.provenance import stamp9random.seed(45)10man = pd.read_parquet(config.manifests_dir() / "corpus_manifest.parquet"); inc = man[man.decision == "include"].copy()11held = []12for (y, t), g in inc.groupby(["bib_year", "article_type"]):13    ids = sorted(g.doc_id.tolist()); k = round(0.2 * len(ids))14    held += random.sample(ids, k)15train = sorted(set(inc.doc_id) - set(held)); held = sorted(held)16def surnames(a): return {x.strip().split()[-1].lower() for x in str(a).split(";") if x.strip()}17tr_auth = set().union(*[surnames(a) for a in inc[inc.doc_id.isin(train)].bib_authors]) if train else set()18overlap = [d for d in held if surnames(inc[inc.doc_id == d].bib_authors.iloc[0]) & tr_auth]19out = {"protocol": "heldout_v1", "seed": 45, "rule": "20% per (year, article_type) stratum, document level", "n_train": len(train), "n_heldout": len(held),20       "heldout_with_author_surname_overlap_in_train": len(overlap), "note": "Author overlap is reported, not eliminated: eliminating it would remove most held-out documents in a single-journal corpus. Profiles are built on train only.",21       "train": train, "heldout": held, **stamp()}22(config.ROOT / "data" / "splits").mkdir(exist_ok=True)23(config.ROOT / "data" / "splits" / "heldout_v1.json").write_text(json.dumps(out, indent=1))24print({k: v for k, v in out.items() if k not in ("train", "heldout", "host")})25
Files · abe8945aefffa0096080b1470e6c1c6a089f5faa
Menu

Theme