A typed-decision model: Qwen/Qwen3.5-2B-Base with its tower fine-tuned and a
trained option-scoring head. It answers choice / noul / score questions about a
document in one forward pass, and speaks the
Jev HTTP API.
This checkpoint is seed 17, fixed in advance as primary rather than chosen for scoring best:
| typed-decisions | reversed order | MMLU-Pro 1k | reproduces its training run |
|---|---|---|---|
| 0.7925 | 0.792 | 0.305 | 1.0000 |
Re-computed from these exact files after upload-time reload. Kernel stack fla-0.5.2/torch-2.7.1+cu128; full recipe in meta.json.
import sys; sys.path.insert(0, 'code') # after snapshot_download of this repo
from load_release import load_release
model, tok, enc, meta = load_release('.', device='cuda')
print(meta['calibration']) # the fitted calibration this checkpoint ships, or 'none'
load_release applies calibration.safetensors when the checkpoint carries one, so the probabilities are the calibrated ones this card reports. A loader that skips those files returns the raw distribution instead: the same chosen option, different numbers.
Everything below is the version record from the project repository, unchanged.
Describes release v2.0 Β· updated 2026-09-26
One typed-decision model, 2B. Given a document and a set of typed questions β yes/no, pick-one-of-k, rate-on-a-rubric β it returns a calibrated probability for every option in one forward pass, with no generated text.
Two things changed from v1.0. It is trained on the train splits of the decision benchmarks it is measured on, which v1.0 never touched. And it carries a fitted confidence head, so the probability it reports means something closer to what it says.
Read section 4 before quoting anything here. On the twelve-benchmark suite v2.0 scores 0.705 against the v1.0 recipe's 0.609. On three benchmarks held out from the entire search it does not beat v1.0. Both facts are measurements of the same model, and the second is the one that answers "is it a better model".
Unchanged from v1.0. A typed decision is a document (the state) plus one or more questions, each of a declared type:
| type | question | the model returns |
|---|---|---|
noul | yes / no | P(true) |
choice | pick one of k named options | a probability per option |
score | rate against a rubric of 2β10 levels | a probability per level, and their expectation |
Pooled top-1 is the fraction of decisions whose highest-probability option matches the teacher's modal label. ECE is expected calibration error: bin decisions by the confidence the model reported, compare each bin's confidence to its accuracy, and average the gaps by bin size. Lower is better, 0 is perfect.
The architecture is v1.0's, unchanged, plus the confidence head in Β§2.1. What changed is the data.
| base | Qwen3.5-2B-Base |
| trained | all tower weights except the frozen input embedding, plus the 7.3 M option_xattn scorer |
| objective | soft cross-entropy on the teacher's distributions, options shuffled per example |
| schedule | 5,774 steps Γ batch 16; tower 5e-6 cosine, head 1e-4 constant |
| precision | tower bf16 autocast + gradient checkpointing, fp32 master; scorer fp32 outside autocast |
| seeds | four (17/29/43/71), judged on the mean, then repeated on four fresh seeds (97/113/131/151); the released checkpoint is seed 17, fixed in advance as primary |
| stack | fla-0.5.2 / torch-2.7.1+cu128 β numbers only compare within one kernel stack |
The training data, in full:
| source | what it is |
|---|---|
n4ze3m/typed-decisions-synth | v1.0's corpus: 6,977 documents with the teacher's full distribution |
LocalLLaMA/typed-decisions, train split, Γ3 | the benchmark's own training data, each case seen three times |
| general multiple-choice replay, 15% of steps | MMLU auxiliary train, ARC, CommonsenseQA, BoolQ and others β there to stop general knowledge eroding |
| the train splits of Kev hard / documents / devtools, Nimble and its ten upstream sources | capped at 3,000 cases per source |
This is the difference that matters, and it cuts both ways. v1.0's headline was a zero-shot number: it had never seen a typed-decisions document. v2.0's is not. Ten of the twelve suite benchmarks contributed training data, so v2.0's score on them measures something v1.0's did not.
What is still never trained on, checked rather than asserted: every benchmark's test split, verified by the arm runner; the three held-out benchmarks in Β§4.3; and the calibration data below. No training document shares a state with any test split.
A linear head predicting one positive temperature per question, which divides that question's logits. Because every option in a row is divided by the same number, the answer never changes β only how sharp the probabilities are. It reads features of the forward pass that already happened (the option distribution's shape, the question type and option count, and a 16-dimensional projection of the decision hidden state), so a decision is still one forward pass.
It is fitted after training, on data withheld from it: 20% of the typed-decisions train cases, 3% of synth, 5% of the replay, and the dev partitions of the suite train splits β 1,576 cases in total were withheld from v2.0's training so the head had something honest to fit on. Score questions are allowed to soften but never to sharpen, which costs a little calibration and keeps the model's score distributions faithful to the teacher's spread.
| calibration method tried | suite ECE | kept |
|---|---|---|
| none (the v2.0 recipe as trained) | 0.0893 | β |
| one global temperature | 0.1073 | no β the model was under-confident on one benchmark and over-confident on others, and one number cancels them out |
| a per-question head | 0.0639 | no β it sharpened score questions and tripled their distance from the teacher |
| a per-question head, score questions floored | 0.0736 | yes |
| reinforcement learning on the confidence (RLCR) | 0.0963 | no β the drift limit that keeps RL stable also stops it moving confidence far enough |
| model | base | typed-decisions | MMLU-Pro 1k | ECE | download |
|---|---|---|---|---|---|
| RSI-Jev-v2.0-2B | Qwen3.5-2B-Base | 0.7925 | 0.305 | 0.0546 | π€ download |
| RSI-Jev-v1.0-2B | Qwen3.5-2B-Base | 0.6525 | 0.3550 | 0.0921 | π€ download |
| RSI-Jev-v1.0-0.8B | Qwen3.5-0.8B-Base | 0.6175 | 0.2690 | β | π€ download |
v2.0's typed-decisions figure is not comparable to v1.0's: v2.0 trained on that benchmark's train split. Its ECE is comparable, and is the honest improvement.
There is no v2.0 at 0.8B. The recipe was only ever run at 2B.
On reproducing its training run. Re-scored from disk with this repo's code, the checkpoint reproduces the training run's per-question predictions at 1.0000 on all three verification targets β typed-decisions in both option orders, and MMLU-Pro at 0.3050. That is the check v1.0's card requires, and it passes.
It is worth knowing what it took to say that cleanly. The same check on a different GPU architecture returned 0.9980 on MMLU-Pro β two questions in a thousand β and 0.3060 rather than 0.3050. Five MMLU-Pro questions have a top-2 logit margin below 0.001, the narrowest 0.0005, and eighteen are below 0.01 against a median of 0.383; reordering an fp32 sum across GPU architectures moves a logit by about that much. So a couple of MMLU-Pro answers are decided by arithmetic order rather than by the model, and MMLU-Pro on this checkpoint should be read as 0.305 Β± 0.001. typed-decisions has no margins that thin and reproduces exactly on every machine tried. The bf16 tower, offered for speed and used for no published number, agrees at 0.9935 / 0.9985 on typed-decisions and 0.9880 on MMLU-Pro.
Every claim above is a file in the checkpoint: verify.json is that re-scoring,
verify_blackwell.json the second machine, roundtrip_200.json the reload check on 200
questions with the calibration applied (200/200, largest probability difference 2.9e-4),
and MANIFEST.json the sha256 of every file so a download can be checked.
A v2.0 checkpoint ships calibration.safetensors and calibration.json beside the
weights. load_release.py applies them automatically; without them the model loads
uncalibrated and its ECE is 0.0893, not 0.0546.
Apache-2.0, following the base model, as v1.0 is.
Four-seed means of each recipe, same evaluator, same kernel stack. The suite mean is
weighted; the weights are in ../BENCHMARKS.md.
| benchmark | weight | v1.0 recipe | v2.0 recipe | v2.0 checkpoint (seed 17) | v2.0 ECE |
|---|---|---|---|---|---|
| typed-decisions | 0.20 | 0.659 | 0.794 | 0.7925 | 0.068 |
| Nimble public | 0.15 | 0.677 | 0.792 | 0.7888 | 0.037 |
| MMLU-Pro 1k | 0.10 | 0.351 | 0.323 | 0.305 | 0.040 |
| Jev-Style panel | 0.10 | 0.734 | 0.736 | 0.7419 | 0.056 |
| Kev transfer | 0.08 | 0.665 | 0.721 | 0.7244 | 0.046 |
| Kev hard | 0.08 | 0.393 | 0.697 | 0.6921 | 0.035 |
| JevBench | 0.06 | 0.663 | 0.716 | 0.7217 | 0.065 |
| Kev documents | 0.05 | 0.714 | 0.865 | 0.8782 | 0.059 |
| Kev devtools | 0.05 | 0.579 | 0.708 | 0.7085 | 0.063 |
| Nimble holdout | 0.05 | 0.565 | 0.751 | 0.7654 | 0.066 |
| procedural | 0.04 | 0.647 | 0.606 | 0.6223 | 0.094 |
| Open-Jev OOD | 0.04 | 0.600 | 0.619 | 0.6237 | 0.057 |
| suite mean | 0.609 | 0.705 | 0.7056 | ||
| suite ECE | 0.0921 | 0.0893 | 0.0546 |
Confirmed, not just measured. The v2.0 recipe was repeated on four seeds it had never been run on, against the previous champion run on those same seeds: 0.7029 against 0.6337, +0.069, higher on all four. Over all eight seeds the gain is +0.0708 and MMLU-Pro is β0.0272.
Ten of these twelve benchmarks contributed train-split data. The two that did not are MMLU-Pro, which fell, and procedural, which also fell. That pattern is the result.
On typed-decisions' 2,000 test decisions, binned by the confidence v2.0 reported:
| the model says | decisions | actually right |
|---|---|---|
| β₯ 0.9 | 539 | 0.983 |
| 0.7 β 0.9 | 509 | 0.833 |
| 0.5 β 0.7 | 707 | 0.713 |
| < 0.5 | 245 | 0.518 |
This is the part that is worth having. v2.0 says 0.9 or better on 539 of the 2,000 decisions and is right on 98.3% of them β nine mistakes. v1.0 reached 0.9 on only 29 decisions out of the same 2,000, so there was almost nothing to act on: it was right when it was confident, and it was hardly ever confident. Over a quarter of this workload can now be decided automatically and the rest routed to something slower.
v1.0's ECE on this split was 0.0978 against v2.0's 0.0678, and the confidence head fixes both directions of the error: the model was under-confident on typed-decisions and over-confident out of distribution.
Three benchmarks were frozen before this work started and read exactly once, after the release model was chosen. Neither model trained on them, so this is the only place where v1.0 and v2.0 are measured on equal terms.
| held out from the whole search | questions | v1.0 | v2.0 | change |
|---|---|---|---|---|
| tasksource | 979 | 0.5771 | 0.5761 | β0.0010 |
| SemIf external | 252 | 0.8492 | 0.8492 | 0.0000 |
| scienthoon OOD | 873 | 0.7148 | 0.6907 | β0.0241 |
v2.0 is not a better decision model than v1.0. It is flat on two of the three and worse on the third. The suite gain of +0.096 is very largely the benefit of having trained on those benchmarks' own data, and it does not travel.
Calibration does travel, partly: ECE improves on scienthoon (0.0824 β 0.0599) and on MMLU-Pro (0.1009 β 0.0399), and gets worse on tasksource (0.0460 β 0.0888), where v2.0 is more confident than v1.0 without being more accurate.
What to use which for. If your documents look like the suite's benchmarks, v2.0 is much stronger on them. If they do not, v1.0 is as good and v2.0's confidence may be optimistic. If you want calibrated probabilities on typed decisions, v2.0.
Unchanged by anything in this release: the confidence head is a dot product on features already computed, and adds no forward pass.
| per decision, document already read | ~10 ms |
| cost model on an NVIDIA GB10 (DGX Spark), bf16 | 52 ms to read the document + 11.5 ms per decision |
Reading the document dominates, which is why a batch of questions about one document is
the shape to ask in. Measure it on your own machine with scripts/bench.py β
../BENCHMARKS.md.
The routing table below is v2.0 on typed-decisions: act on the most confident x% of decisions and defer the rest.
| act on | accuracy of what you acted on |
|---|---|
| 100% | 0.792 |
| 80% | 0.851 |
| 60% | 0.892 |
| 40% | 0.945 |
| 20% | 0.995 |
confidence field is not the probabilityThe API returns both, and they are different numbers. The probability is the model's mass
on an option. confidence is the peak statistic Jev documents,
(K * p_max - 1) / (K - 1) β for three options, "(3 x largest probability - 1) / 2". It
measures how peaked the whole distribution is, is 0 at uniform and 1 at one-hot, and is
absent from noul answers.
What v2.0 changes is the input to that formula, not the formula. The confidence head
rescales the probabilities, so confidence moves with them. Route on the probability of
the option you intend to act on, as Β§4.2 and the table above do; use
confidence when what you want to know is whether the model is spread across options.
Because v2.0's probabilities are better calibrated, a threshold chosen on one document set transfers better than it did with v1.0 β within the caveat in Β§4.3, which is that on unfamiliar documents v2.0 is the more confident model without being the more accurate one.
Unchanged from v1.0 Β§7; the weights are the same size and the calibration files add 140 KB.
Nothing yet.
rsijev/targets_suite.py, scripts/suite.py --list) and every split is pinned to a
public upstream commit, so the headline is reproducible β but you fetch four or five
repositories yourself, because this repo redistributes none of them. Two of the three
held-out benchmarks come from upstreams that have since gone private and survive only as
vendored copies inside the Kev repo.../rsijev/README.md). What is missing is data: the replay pool's
source files, which came from an external task registry, and the frozen suite definitions
that the train-split conversion decontaminates against. v1.0 needed only
scripts/build_synth_corpus.py, so v2.0 is a step harder to check, and closing it is a
data release rather than a code one.v1.0 came out of five turns that each ruled something out:
| where it went | typed-decisions | what it established |
|---|---|---|
| the frozen base, read out by its own logprobs | 0.3775 | a base model on its own sits below the majority baseline |
| a trained readout head on a frozen tower | 0.4850 | the head is not the bottleneck |
| the same head, trained on synthetic data | 0.483 | neither is the data β the frozen tower is |
| fine-tune the tower, 0.8B | 0.6097 | capability is the lever: +0.125 in one step |
| the same recipe at 2B | 0.6598 | scale helps, and surfaces an instability |
| v1.0 | 0.662 | the instability was precision, not the optimiser |
Then about fifty more arms, of which four were kept: the benchmark's own train split with general-knowledge replay, the other benchmarks' train splits, and two forms of the confidence head. Every training-objective arm and every reinforcement-learning arm was rejected β including five separate RL rewards on the decision itself, and a reasoning teacher that scores 0.677 zero-shot but disagrees with the benchmark's teacher precisely on the ambiguous items.
The chain that produced this release, out of those fifty:
| arm | headline | what it established |
|---|---|---|
spec-1-synth-plus-td-train | typed-decisions 0.7794 | training on the benchmark's own train split is worth +0.12 β and costs MMLU-Pro, so it was rejected |
spec-2-x3-plus-mc-replay-r15 | typed-decisions 0.796 | 15% general-knowledge replay pays the MMLU-Pro cost back. The first keeper |
suite-train-1-cap1k | suite 0.6932 | the same lever on the other benchmarks' train splits, at 1k cases per source |
suite-train-1-cap3k | suite 0.7049 | 3k per source is better. v2.0's recipe |
suite-train-1-cap3k-confirm | suite 0.7029 | +0.069 on four seeds it had never been run on, paired against the champion |
cal-1-global-temperature | suite ECE 0.1073 | one temperature cannot fix confidence that errs in both directions |
cal-4-oof-confidence-head | suite ECE 0.0639 | a per-question head can. The calibration keeper |
cal-4b-oof-scorefloor | suite ECE 0.0736 | stop it sharpening score questions and their distributions stay faithful. Shipped |
rc-A-cap3k-cal4b | suite 0.7056, ECE 0.0546 | the two together, seed 17. This checkpoint |
The other forty-odd directions were rejected. What each one was, what it scored and why it
failed is the search record, not this release's record, and it is in
../EXPLORE.md.
One bar was moved after seeing a result, and it should be read with that in mind. The recipe that became v2.0 first failed the MMLU-Pro guard at β0.026 against a 0.020 limit. The run owner widened that limit to 0.030 on the grounds that MMLU-Pro is a guard against forgetting rather than a target. The original rejection is still in the log.
A typed-decision model: Qwen/Qwen3.5-2B-Base with its tower fine-tuned and a
trained option-scoring head. It answers choice / noul / score questions about a
document in one forward pass, and speaks the
Jev HTTP API.
This checkpoint is seed 17, fixed in advance as primary rather than chosen for scoring best:
| typed-decisions | reversed order | MMLU-Pro 1k | reproduces its training run |
|---|---|---|---|
| 0.7925 | 0.792 | 0.305 | 1.0000 |
Re-computed from these exact files after upload-time reload. Kernel stack fla-0.5.2/torch-2.7.1+cu128; full recipe in meta.json.
import sys; sys.path.insert(0, 'code') # after snapshot_download of this repo
from load_release import load_release
model, tok, enc, meta = load_release('.', device='cuda')
print(meta['calibration']) # the fitted calibration this checkpoint ships, or 'none'
load_release applies calibration.safetensors when the checkpoint carries one, so the probabilities are the calibrated ones this card reports. A loader that skips those files returns the raw distribution instead: the same chosen option, different numbers.
Everything below is the version record from the project repository, unchanged.
Describes release v2.0 Β· updated 2026-09-26
One typed-decision model, 2B. Given a document and a set of typed questions β yes/no, pick-one-of-k, rate-on-a-rubric β it returns a calibrated probability for every option in one forward pass, with no generated text.
Two things changed from v1.0. It is trained on the train splits of the decision benchmarks it is measured on, which v1.0 never touched. And it carries a fitted confidence head, so the probability it reports means something closer to what it says.
Read section 4 before quoting anything here. On the twelve-benchmark suite v2.0 scores 0.705 against the v1.0 recipe's 0.609. On three benchmarks held out from the entire search it does not beat v1.0. Both facts are measurements of the same model, and the second is the one that answers "is it a better model".
Unchanged from v1.0. A typed decision is a document (the state) plus one or more questions, each of a declared type:
| type | question | the model returns |
|---|---|---|
noul | yes / no | P(true) |
choice | pick one of k named options | a probability per option |
score | rate against a rubric of 2β10 levels | a probability per level, and their expectation |
Pooled top-1 is the fraction of decisions whose highest-probability option matches the teacher's modal label. ECE is expected calibration error: bin decisions by the confidence the model reported, compare each bin's confidence to its accuracy, and average the gaps by bin size. Lower is better, 0 is perfect.
The architecture is v1.0's, unchanged, plus the confidence head in Β§2.1. What changed is the data.
| base | Qwen3.5-2B-Base |
| trained | all tower weights except the frozen input embedding, plus the 7.3 M option_xattn scorer |
| objective | soft cross-entropy on the teacher's distributions, options shuffled per example |
| schedule | 5,774 steps Γ batch 16; tower 5e-6 cosine, head 1e-4 constant |
| precision | tower bf16 autocast + gradient checkpointing, fp32 master; scorer fp32 outside autocast |
| seeds | four (17/29/43/71), judged on the mean, then repeated on four fresh seeds (97/113/131/151); the released checkpoint is seed 17, fixed in advance as primary |
| stack | fla-0.5.2 / torch-2.7.1+cu128 β numbers only compare within one kernel stack |
The training data, in full:
| source | what it is |
|---|---|
n4ze3m/typed-decisions-synth | v1.0's corpus: 6,977 documents with the teacher's full distribution |
LocalLLaMA/typed-decisions, train split, Γ3 | the benchmark's own training data, each case seen three times |
| general multiple-choice replay, 15% of steps | MMLU auxiliary train, ARC, CommonsenseQA, BoolQ and others β there to stop general knowledge eroding |
| the train splits of Kev hard / documents / devtools, Nimble and its ten upstream sources | capped at 3,000 cases per source |
This is the difference that matters, and it cuts both ways. v1.0's headline was a zero-shot number: it had never seen a typed-decisions document. v2.0's is not. Ten of the twelve suite benchmarks contributed training data, so v2.0's score on them measures something v1.0's did not.
What is still never trained on, checked rather than asserted: every benchmark's test split, verified by the arm runner; the three held-out benchmarks in Β§4.3; and the calibration data below. No training document shares a state with any test split.
A linear head predicting one positive temperature per question, which divides that question's logits. Because every option in a row is divided by the same number, the answer never changes β only how sharp the probabilities are. It reads features of the forward pass that already happened (the option distribution's shape, the question type and option count, and a 16-dimensional projection of the decision hidden state), so a decision is still one forward pass.
It is fitted after training, on data withheld from it: 20% of the typed-decisions train cases, 3% of synth, 5% of the replay, and the dev partitions of the suite train splits β 1,576 cases in total were withheld from v2.0's training so the head had something honest to fit on. Score questions are allowed to soften but never to sharpen, which costs a little calibration and keeps the model's score distributions faithful to the teacher's spread.
| calibration method tried | suite ECE | kept |
|---|---|---|
| none (the v2.0 recipe as trained) | 0.0893 | β |
| one global temperature | 0.1073 | no β the model was under-confident on one benchmark and over-confident on others, and one number cancels them out |
| a per-question head | 0.0639 | no β it sharpened score questions and tripled their distance from the teacher |
| a per-question head, score questions floored | 0.0736 | yes |
| reinforcement learning on the confidence (RLCR) | 0.0963 | no β the drift limit that keeps RL stable also stops it moving confidence far enough |
| model | base | typed-decisions | MMLU-Pro 1k | ECE | download |
|---|---|---|---|---|---|
| RSI-Jev-v2.0-2B | Qwen3.5-2B-Base | 0.7925 | 0.305 | 0.0546 | π€ download |
| RSI-Jev-v1.0-2B | Qwen3.5-2B-Base | 0.6525 | 0.3550 | 0.0921 | π€ download |
| RSI-Jev-v1.0-0.8B | Qwen3.5-0.8B-Base | 0.6175 | 0.2690 | β | π€ download |
v2.0's typed-decisions figure is not comparable to v1.0's: v2.0 trained on that benchmark's train split. Its ECE is comparable, and is the honest improvement.
There is no v2.0 at 0.8B. The recipe was only ever run at 2B.
On reproducing its training run. Re-scored from disk with this repo's code, the checkpoint reproduces the training run's per-question predictions at 1.0000 on all three verification targets β typed-decisions in both option orders, and MMLU-Pro at 0.3050. That is the check v1.0's card requires, and it passes.
It is worth knowing what it took to say that cleanly. The same check on a different GPU architecture returned 0.9980 on MMLU-Pro β two questions in a thousand β and 0.3060 rather than 0.3050. Five MMLU-Pro questions have a top-2 logit margin below 0.001, the narrowest 0.0005, and eighteen are below 0.01 against a median of 0.383; reordering an fp32 sum across GPU architectures moves a logit by about that much. So a couple of MMLU-Pro answers are decided by arithmetic order rather than by the model, and MMLU-Pro on this checkpoint should be read as 0.305 Β± 0.001. typed-decisions has no margins that thin and reproduces exactly on every machine tried. The bf16 tower, offered for speed and used for no published number, agrees at 0.9935 / 0.9985 on typed-decisions and 0.9880 on MMLU-Pro.
Every claim above is a file in the checkpoint: verify.json is that re-scoring,
verify_blackwell.json the second machine, roundtrip_200.json the reload check on 200
questions with the calibration applied (200/200, largest probability difference 2.9e-4),
and MANIFEST.json the sha256 of every file so a download can be checked.
A v2.0 checkpoint ships calibration.safetensors and calibration.json beside the
weights. load_release.py applies them automatically; without them the model loads
uncalibrated and its ECE is 0.0893, not 0.0546.
Apache-2.0, following the base model, as v1.0 is.
Four-seed means of each recipe, same evaluator, same kernel stack. The suite mean is
weighted; the weights are in ../BENCHMARKS.md.
| benchmark | weight | v1.0 recipe | v2.0 recipe | v2.0 checkpoint (seed 17) | v2.0 ECE |
|---|---|---|---|---|---|
| typed-decisions | 0.20 | 0.659 | 0.794 | 0.7925 | 0.068 |
| Nimble public | 0.15 | 0.677 | 0.792 | 0.7888 | 0.037 |
| MMLU-Pro 1k | 0.10 | 0.351 | 0.323 | 0.305 | 0.040 |
| Jev-Style panel | 0.10 | 0.734 | 0.736 | 0.7419 | 0.056 |
| Kev transfer | 0.08 | 0.665 | 0.721 | 0.7244 | 0.046 |
| Kev hard | 0.08 | 0.393 | 0.697 | 0.6921 | 0.035 |
| JevBench | 0.06 | 0.663 | 0.716 | 0.7217 | 0.065 |
| Kev documents | 0.05 | 0.714 | 0.865 | 0.8782 | 0.059 |
| Kev devtools | 0.05 | 0.579 | 0.708 | 0.7085 | 0.063 |
| Nimble holdout | 0.05 | 0.565 | 0.751 | 0.7654 | 0.066 |
| procedural | 0.04 | 0.647 | 0.606 | 0.6223 | 0.094 |
| Open-Jev OOD | 0.04 | 0.600 | 0.619 | 0.6237 | 0.057 |
| suite mean | 0.609 | 0.705 | 0.7056 | ||
| suite ECE | 0.0921 | 0.0893 | 0.0546 |
Confirmed, not just measured. The v2.0 recipe was repeated on four seeds it had never been run on, against the previous champion run on those same seeds: 0.7029 against 0.6337, +0.069, higher on all four. Over all eight seeds the gain is +0.0708 and MMLU-Pro is β0.0272.
Ten of these twelve benchmarks contributed train-split data. The two that did not are MMLU-Pro, which fell, and procedural, which also fell. That pattern is the result.
On typed-decisions' 2,000 test decisions, binned by the confidence v2.0 reported:
| the model says | decisions | actually right |
|---|---|---|
| β₯ 0.9 | 539 | 0.983 |
| 0.7 β 0.9 | 509 | 0.833 |
| 0.5 β 0.7 | 707 | 0.713 |
| < 0.5 | 245 | 0.518 |
This is the part that is worth having. v2.0 says 0.9 or better on 539 of the 2,000 decisions and is right on 98.3% of them β nine mistakes. v1.0 reached 0.9 on only 29 decisions out of the same 2,000, so there was almost nothing to act on: it was right when it was confident, and it was hardly ever confident. Over a quarter of this workload can now be decided automatically and the rest routed to something slower.
v1.0's ECE on this split was 0.0978 against v2.0's 0.0678, and the confidence head fixes both directions of the error: the model was under-confident on typed-decisions and over-confident out of distribution.
Three benchmarks were frozen before this work started and read exactly once, after the release model was chosen. Neither model trained on them, so this is the only place where v1.0 and v2.0 are measured on equal terms.
| held out from the whole search | questions | v1.0 | v2.0 | change |
|---|---|---|---|---|
| tasksource | 979 | 0.5771 | 0.5761 | β0.0010 |
| SemIf external | 252 | 0.8492 | 0.8492 | 0.0000 |
| scienthoon OOD | 873 | 0.7148 | 0.6907 | β0.0241 |
v2.0 is not a better decision model than v1.0. It is flat on two of the three and worse on the third. The suite gain of +0.096 is very largely the benefit of having trained on those benchmarks' own data, and it does not travel.
Calibration does travel, partly: ECE improves on scienthoon (0.0824 β 0.0599) and on MMLU-Pro (0.1009 β 0.0399), and gets worse on tasksource (0.0460 β 0.0888), where v2.0 is more confident than v1.0 without being more accurate.
What to use which for. If your documents look like the suite's benchmarks, v2.0 is much stronger on them. If they do not, v1.0 is as good and v2.0's confidence may be optimistic. If you want calibrated probabilities on typed decisions, v2.0.
Unchanged by anything in this release: the confidence head is a dot product on features already computed, and adds no forward pass.
| per decision, document already read | ~10 ms |
| cost model on an NVIDIA GB10 (DGX Spark), bf16 | 52 ms to read the document + 11.5 ms per decision |
Reading the document dominates, which is why a batch of questions about one document is
the shape to ask in. Measure it on your own machine with scripts/bench.py β
../BENCHMARKS.md.
The routing table below is v2.0 on typed-decisions: act on the most confident x% of decisions and defer the rest.
| act on | accuracy of what you acted on |
|---|---|
| 100% | 0.792 |
| 80% | 0.851 |
| 60% | 0.892 |
| 40% | 0.945 |
| 20% | 0.995 |
confidence field is not the probabilityThe API returns both, and they are different numbers. The probability is the model's mass
on an option. confidence is the peak statistic Jev documents,
(K * p_max - 1) / (K - 1) β for three options, "(3 x largest probability - 1) / 2". It
measures how peaked the whole distribution is, is 0 at uniform and 1 at one-hot, and is
absent from noul answers.
What v2.0 changes is the input to that formula, not the formula. The confidence head
rescales the probabilities, so confidence moves with them. Route on the probability of
the option you intend to act on, as Β§4.2 and the table above do; use
confidence when what you want to know is whether the model is spread across options.
Because v2.0's probabilities are better calibrated, a threshold chosen on one document set transfers better than it did with v1.0 β within the caveat in Β§4.3, which is that on unfamiliar documents v2.0 is the more confident model without being the more accurate one.
Unchanged from v1.0 Β§7; the weights are the same size and the calibration files add 140 KB.
Nothing yet.
rsijev/targets_suite.py, scripts/suite.py --list) and every split is pinned to a
public upstream commit, so the headline is reproducible β but you fetch four or five
repositories yourself, because this repo redistributes none of them. Two of the three
held-out benchmarks come from upstreams that have since gone private and survive only as
vendored copies inside the Kev repo.../rsijev/README.md). What is missing is data: the replay pool's
source files, which came from an external task registry, and the frozen suite definitions
that the train-split conversion decontaminates against. v1.0 needed only
scripts/build_synth_corpus.py, so v2.0 is a step harder to check, and closing it is a
data release rather than a code one.v1.0 came out of five turns that each ruled something out:
| where it went | typed-decisions | what it established |
|---|---|---|
| the frozen base, read out by its own logprobs | 0.3775 | a base model on its own sits below the majority baseline |
| a trained readout head on a frozen tower | 0.4850 | the head is not the bottleneck |
| the same head, trained on synthetic data | 0.483 | neither is the data β the frozen tower is |
| fine-tune the tower, 0.8B | 0.6097 | capability is the lever: +0.125 in one step |
| the same recipe at 2B | 0.6598 | scale helps, and surfaces an instability |
| v1.0 | 0.662 | the instability was precision, not the optimiser |
Then about fifty more arms, of which four were kept: the benchmark's own train split with general-knowledge replay, the other benchmarks' train splits, and two forms of the confidence head. Every training-objective arm and every reinforcement-learning arm was rejected β including five separate RL rewards on the decision itself, and a reasoning teacher that scores 0.677 zero-shot but disagrees with the benchmark's teacher precisely on the ambiguous items.
The chain that produced this release, out of those fifty:
| arm | headline | what it established |
|---|---|---|
spec-1-synth-plus-td-train | typed-decisions 0.7794 | training on the benchmark's own train split is worth +0.12 β and costs MMLU-Pro, so it was rejected |
spec-2-x3-plus-mc-replay-r15 | typed-decisions 0.796 | 15% general-knowledge replay pays the MMLU-Pro cost back. The first keeper |
suite-train-1-cap1k | suite 0.6932 | the same lever on the other benchmarks' train splits, at 1k cases per source |
suite-train-1-cap3k | suite 0.7049 | 3k per source is better. v2.0's recipe |
suite-train-1-cap3k-confirm | suite 0.7029 | +0.069 on four seeds it had never been run on, paired against the champion |
cal-1-global-temperature | suite ECE 0.1073 | one temperature cannot fix confidence that errs in both directions |
cal-4-oof-confidence-head | suite ECE 0.0639 | a per-question head can. The calibration keeper |
cal-4b-oof-scorefloor | suite ECE 0.0736 | stop it sharpening score questions and their distributions stay faithful. Shipped |
rc-A-cap3k-cal4b | suite 0.7056, ECE 0.0546 | the two together, seed 17. This checkpoint |
The other forty-odd directions were rejected. What each one was, what it scored and why it
failed is the search record, not this release's record, and it is in
../EXPLORE.md.
One bar was moved after seeing a result, and it should be read with that in mind. The recipe that became v2.0 first failed the MMLU-Pro guard at β0.026 against a 0.020 limit. The run owner widened that limit to 0.030 on the grounds that MMLU-Pro is a guard against forgetting rather than a target. The original rejection is still in the log.