famulus-logic/
config/
needle/
questions.json
relations.json
strength.json
support.json
data/
cache/
needle/
benchmark.json
sentences.json
docs/
_extensions/
_generiert/
famulus-logic_files/
argument-reconstruction.md
auswertung.md
famulus-logic.html
famulus-logic.pdf
famulus-logic.qmd
lettreai.typ
nadel-audit.pdf
nadel-audit.qmd
examples/
e57/
Möglichkeiten zur effizienten Satzklassifikation mit DAB Records auf M1 _ Shared Grok Conversation_files/
0--eshig294o9.js
00vg6jt0fvbe9.js
04fx73_34obf_.css
06objgmqrmr5-.js
0766cf6fm-whk.js
07eff-1nsnp-7.js
08thfeb2tpc8n.js
0_3yfs9r86fla.css
0_5qo0wbjggzn.js
0_cwmk02s8mj0.js
0aeevy4irfung.js
0ak1hinf2cwbs.js
0aul3dl80nh3u.js
0c-d5t8wyinmo.css
0cw04dvb6goo0.js
prompts/
argument_sketch.md
classify_list.md
classify_pair.md
classify_pair_weak.md
probe_generation.md
support_set.md
support_triad.md
runs/
argue/
cache/
gold-v2/
needle/
20261011T120341Z-lexical-baseline-591f20ff.json
20261011T120353Z-llm-f0ad2158.json
20261011T121601Z-llm-5a18b15b.json
20261011T121601Z-llm-f0ad2158.json
20261011T123544Z-triad-llm-d8415be8.json
Benchmark for classifiers that judge whether a probing expression P stands in a logical relation to any sentence of a list drawn from the PDAI collections — and in which relation. Consequence is not restricted to material implication: conceptual rules (Junggeselle → unverheirateter Mann), synonymy, hyponymy, converse relations, calendar arithmetic and geographic inclusion all count, provided the rule is a rule of meaning and not an unstated fact.
Every sentence and every probe must be an Aussage (true or false).
PDAI page XML / fresh index.duckdb
│ harvest split, Aussage pre-filter, provenance (path, OCR model, sha256, mtime)
▼
data/sentences.json
│ probe LLM: confirm Aussage · probes for each target relation · near misses
▼
data/benchmark.json sentences with `attributes` = gold labels per probe
│ bench probe × [source sentence + distractors] → classifier
▼
runs/bench.duckdb `runs` (one row per run: error matrix, wall time, classifier properties)
`predictions` (one row per pair) · view `leaderboard`
runs/<run_id>.json full run record
| file | content |
|---|---|
config/relations.json |
the relation catalog: 7 labels with description and how to ascertain, the four-cell decision procedure, bases (grounds of a relation), near-miss types, Aussage admission rules |
prompts/probe_generation.md |
generator instruction (catalog is rendered in) |
prompts/classify_pair.md, prompts/classify_list.md |
classifier instructions, one pair per call or a whole list per call |
src/famulus_logic/ |
harvest, aussage, probes, bench, metrics, store, classifiers/ |
tests/fixtures/mini_benchmark.json |
synthetic fixture (not PDAI text) |
Each label is defined by the truth-value combinations of (S, P) that are impossible; classifiers judge the four cells and the label follows.
| label | impossible | reading |
|---|---|---|
equivalent |
TF, FT | S ⊨ P and P ⊨ S |
entails |
TF | S ⊨ P, P weaker |
entailed_by |
FT | P ⊨ S, P stronger |
contradictory |
TT, FF | exactly one true |
contrary |
TT | not both true, both may be false |
subcontrary |
FF | not both false |
independent |
— | all four possible |
Families for the coarse matrix: follows (first three), opposes (next three), none.
Probes built to look like a relation (mimics) while their gold label is
another one: converse direction, overlap without rule, false synonym, role
swap, quantifier shift, modal shift, temporal shift, entity substitution,
negation scope, contrary-as-contradictory, attitude drop, missing premise.
The trap rate is the share of near misses a classifier labels as the
relation they mimic.
uv sync --extra dev
uv run famulus-logic relations
# 1) sentences (default root $PDAI_ROOT or /Volumes/golden4T/pdai-collections, canonical layout)
uv run famulus-logic harvest --collections kepler-prim karman-nachlass --per-doc 200
# local snapshots while the drive is offline:
uv run famulus-logic harvest --root ~/ai-mac-air/pdai/collections \
--glob 'kirch/quality/dual-read/*/page_*.xml' 'hevelius/pilot/*/page_*.xml' --per-doc 150
# 2) probes (cached per sentence; resumes after interruption)
uv run famulus-logic probe --model deepseek-v4.1-flash:cloud --limit 500 --workers 8
# 3) runs
uv run famulus-logic bench --classifier lexical
uv run famulus-logic bench --classifier fast --split 0.7
uv run famulus-logic bench --classifier llm:kimi-k3:cloud --mode list --decide cells
uv run famulus-logic report # leaderboard
uv run famulus-logic report --run <run_id> # error matrix of one run
uv run famulus-logic audit --run <run_id> # disagreements → runs/audit.jsonl for gold review
LLM backend: any OpenAI-compatible endpoint; default local Ollama
(FAMULUS_LOGIC_LLM_BASE=http://localhost:11434/v1, FAMULUS_LOGIC_LLM_KEY).
The fast classifier (TF-IDF + logistic regression, sentences held in an
in-memory DuckDB table) needs the optional fast extra: uv sync --extra fast.
runs row: classifier name, version, model, mode (pair/list), decision
(cells/label), all properties (temperature, seed, prompt-template sha256,
relations sha256), benchmark sha256, task parameters, environment (host,
python, git commit + dirty flag) — and the results: accuracy, macro/weighted
F1, Cohen's κ, the fine 7×7 and coarse 3×3 error matrices, related-vs-independent
F1, accuracy on positives vs. near misses, trap rate, distractor false-related
rate, list-level detection F1 / localization / exact-list accuracy, wall
time, pairs/s, latency p50/p95, tokens in/out, error counts.
docs/famulus-logic.qmd (German; HTML + PDF, lettreai theme) describes the catalog, the pipeline, the metrics and the pilot results. Tables come from scripts/docs_generate.py; refresh after every run:
uv run python scripts/docs_generate.py
cd docs && quarto render famulus-logic.qmd --to lettreai-html
QUARTO_TYPST=$(which typst) quarto render famulus-logic.qmd --to lettreai-typst
A second layer on top of the pairwise relations: inferential contribution.
Does the premise pair (A, B) support a conclusion C, and how? The judge marks
the eight truth-value cells of (A, B, C). The label (linked, convergent,
a_suffices, restates_a, a_necessary, linked_against, … 17 in all) is
computed from them as prime implicants, with impossible premise
combinations as don't-cares. For n premises, n + 2 cells decide minimal
sufficiency.
On top of that test, argue reconstructs the argument DAG of a section
the way a minimal theory is built in the regularity theory of causation:
The full account, with Euler's E57 §§ 9–10 as the worked example, is in docs/argument-reconstruction.md.
| file | content |
|---|---|
config/support.json |
support catalog: standards, eight cells, 17 labels, unit/node kinds, exclusion reasons, indicator lexicon (la/de/en/fr) |
prompts/support_triad.md, support_set.md, argument_sketch.md |
judge (8 cells / n + 2 cells) and proposer instructions |
src/famulus_logic/argument/ |
support (cell logic), section, graph, judge, propose, reconstruct, triad |
examples/e57/ |
E57 section (PDAI page 006, provenance), gold reconstruction in two readings, distractors, triads, generated trees in out/ |
tests/fixtures/triads.json |
20 synthetic three-sentence items covering every label and seven near-miss types |
uv run famulus-logic support
uv run famulus-logic triad --judge llm:kimi-k3:cloud # tests/fixtures/triads.json
uv run famulus-logic triad --items examples/e57/triads.json --judge llm:kimi-k3:cloud
uv run famulus-logic argue --section examples/e57/section.json --reading Q --distractors # oracle
uv run famulus-logic argue --section examples/e57/section.json --reading Q --distractors \
--proposer llm:deepseek-v4.1-flash:cloud --judge llm:deepseek-v4.1-flash:cloud
gold_status is
generated when its four-cell judgement matches its label, otherwise
inconsistent_cells (excluded from runs). Use audit and set
gold_status to verified/human after review. Do not benchmark the
generator model against its own gold without saying so.independent). Same-document distractors
(assumed:same_doc) are harder and occasionally truly related; they are
reported separately in metrics.distractors.harvest uses index.duckdb only if it is not older
than the page OCR XML of its document; otherwise it reads the XML and counts
index_stale. Sentence text is never altered beyond whitespace.