Two chess engines and one illegal move

Imagine two teams training the same chess system. Both use the same neural network, the same self-play budget and the same tree search. Team A exposes only legal moves at each position. Team B lets the system propose any pair of squares, executes the proposal when possible and supplies a large negative reward whenever the move is illegal.

Team B can make a principled argument. Legality is part of the environment. Given enough experience, the learner should internalise it. A separate legal-move generator encodes human knowledge and therefore appears to violate the lesson that general methods eventually beat hand-crafted ones. Team A replies that legality is not chess strategy. It is an exact boundary around the action space. Removing it spends learning and search on rediscovering a compact invariant, while allowing an avoidable class of invalid actions during training.

The dispute becomes sharper outside a game. Suppose the proposed action is not moving a bishop but releasing a payment, changing a medication dose or opening an industrial valve. The environment may reveal the mistake only after an irreversible effect. The number of failures required to learn a rule is then part of the engineering cost, and “the model will eventually learn” is not the same claim as “the system will never execute this known-forbidden action”.

The central argument is that scale should own discovery, while explicit structure should own only narrow admissibility and verification boundaries that can be stated more reliably than they can be learned from consequences. This is not a truce between two schools. It is a causal placement rule. Learned systems earn their advantage where useful behaviour lies in a large, changing space and feedback can guide search. Symbolic checks earn theirs where a small proposition is exact, observable and costly to violate.

This distinction changes the architecture. Instead of asking whether a system is neural or symbolic, ask two separate questions. What mechanism should produce promising actions? What mechanism is entitled to declare an action admissible? The first question normally favours learning and search. The second sometimes has an answer small enough to test exhaustively.

Part I

What the bitter lesson actually teaches

Richard Sutton’s 2019 essay compresses a recurring historical pattern. Researchers encode their understanding of a domain, gain an early advantage, then watch a more general method overtake it as computation becomes cheaper. Sutton identifies search and learning as the methods that can keep absorbing additional computation. The warning is directed at attempts to build the contents of human thought into an intelligent system, particularly when that knowledge becomes a ceiling on improvement.1

AlphaZero is a compelling exhibit. Earlier chess engines combined deep search with large stores of evaluation knowledge and domain-specific engineering. AlphaZero began from random play and, apart from the rules, used one reinforcement-learning and search procedure across chess, shogi and Go. It learned its evaluation and policy through self-play rather than inheriting a catalogue of human strategies.2 The result strongly supports abandoning hand-authored strategic judgement when a scalable learning loop can generate better judgement.

Yet the phrase “apart from the rules” matters. AlphaZero did not need to learn that a bishop moves diagonally by crashing into millions of illegal transitions. The rules defined the simulator, legal actions and terminal conditions within which search and learning operated. That structure did not tell the system which legal move was good. It made the search problem well formed.

MuZero pushes much further towards the bitter lesson. It learns a latent dynamics model sufficient for predicting reward, policy and value, then plans inside that learned model. On Go, chess and shogi it matched AlphaZero without being supplied the game dynamics; on Atari it combined learned dynamics with search across visually complex environments.3 This is strong evidence that even apparently foundational domain structure can sometimes be learned.

MuZero also exposes the qualifier. More search helped substantially in Go, but its gains plateaued in Atari, which the authors associated with model inaccuracy. Search cannot repair a future model that becomes wrong as it rolls forward. Additional computation amplifies whatever transition and value structure the system has learned. Compute is a multiplier, not a substitute for the correctness of the world on which the computation operates.

The bitter lesson is best read as an investment prior: before encoding domain judgement, test whether data, search and compute can discover a better version. The more open-ended the target, the stronger that prior.

It is weaker as a claim about small, extensional boundaries. A legal-move predicate, a type checker and a cryptographic signature test do not attempt to reproduce the contents of intelligence. They reject a formally characterised subset of outputs. Their value does not come from outperforming learning at strategy. It comes from making one proposition decidable before an effect.

The lesson has a jurisdiction: it attacks hand-crafted solutions to open-ended intelligence, not every compact constraint that defines a valid interaction. Extending it beyond that jurisdiction turns a historical observation into an ideology.

Figure 2. The legal-move membrane does not choose the strategy

Legal move membrane A cloud of candidate chess moves passes through a thin legal-move membrane. Legal moves continue to a learned search landscape, while illegal moves are rejected without being ranked as strategy. Candidate moves legal? Learned value and tree search Legality removes invalid moves; search still chooses the move.
Conceptual thought experiment. The structural correspondence is exact: the membrane represents a decidable legal-action predicate, while the landscape represents open-ended strategic value. The analogy fails when “legality” itself is ambiguous or depends on unobserved state.

Three kinds of structure that should not be collapsed

Arguments about neuro-symbolic systems often treat all human contribution as “knowledge”. That makes the debate impossible to resolve. At least three different objects are being mixed.

First, there is inductive structure. A convolution assumes locality; attention supplies content-addressed interaction; a tree search assumes that imagined continuations are worth comparing. These structures shape what learning can discover efficiently. They are not normally lists of domain facts, and they remain subject to the bitter lesson: a better general architecture may displace them.

Second, there is strategic domain knowledge. Examples include a hand-written chess evaluation, a catalogue of visual features or a large expert-rule system that tries to decide what to do. This is the bitter lesson’s clearest target. Such knowledge can bring data efficiency, but it often freezes the designer’s decomposition and fails to absorb increased compute.

Third, there is admissibility and verification structure. Examples include a grammar, a type relation, a conservation law, a policy threshold, a proof kernel or a precondition on a tool call. This structure does not need to rank every possible action. It says that a candidate cannot be released unless a proposition holds.

The third category is not automatically good. A giant rule base can become another brittle expert system. A local checker can still encode the wrong rule. The relevant question is whether the proposition is smaller, more stable and more directly testable than the behaviour being generated. When it is, explicit representation can reduce the burden on learning without prescribing the solution.

Part II

Why rare constraints survive scale

The strongest causal case for explicit constraint is not that neural networks are incapable of learning rules. It is that some important rules are observed mainly through their violation, while the violations are deliberately rare. A learner cannot infer an exception it never encounters unless it transfers the rule from other evidence or receives it through the training objective.

Let an independently sampled action encounter a particular exception with probability ε. After n observations, the probability of seeing at least one such exception is:

P(seen ≥ 1 exception) = 1 − (1 − ε)n ε is the exception rate and n is the number of observed actions. Increasing either term raises the chance of observing the failure.

To reach confidence 1 − δ of seeing even one example, the required count is:

n ≥ ln(δ) / ln(1 − ε) ≈ ln(1/δ) / ε δ is the tolerated probability of seeing no example. The approximation holds when ε is small. It counts one encounter, not enough data to estimate a complex rule or establish a low failure rate.

At an exception rate of 0.1 per cent, roughly 2,995 observations give a 95 per cent chance of seeing one case. At one per million, the count is about three million. Conjunctive rules need the relevant combinations, and time-varying rules make old samples less probative.

Rare-event sample complexity creates a region where an explicit rule can be cheaper than empirical rediscovery, even though learning would eventually approximate it. The word “cheaper” includes failed actions, delayed release, human labelling and the evidence required to demonstrate a residual risk.

Figure 3. One observed exception can require millions of ordinary actions

Rare exception sample curve A log-log curve shows the observations required for a 95 per cent chance of seeing at least one exception as exception frequency falls from one in ten to one in a million. 0.1% → 2,995 1 in 1,000,000 → ≈3.0m common exception rare exception → observations for 95% encounter chance → Log axes: cost of one encounter, before estimating the rule.
Calculated from 1 − (1 − ε)n, using a 95 per cent encounter threshold. Values are analytic, not model benchmark results. The denominator is independently sampled actions.

Thought experiment: change only rarity, then only consequence

Consider two plants with identical sensors, controllers and actions. In Plant A, a wrong route occurs one time in twenty, pauses a conveyor for five minutes and resets. The error is visible, reversible and frequent, so a reinforcement learner can explore and improve.

Hold the task fixed but reduce the exception to one in a million. The learner now receives far less evidence. Hold rarity fixed again and make the effect an irreversible contaminant release. The learning problem is unchanged, but the exploration budget collapses.

Rarity controls whether feedback arrives; consequence controls whether discovery by violation is tolerable. High values on both axes require information from simulation, synthetic counterexamples, a formal constraint, human review or some combination.

A symbolic guard is not the only response. Oversampling, simulation, transfer and verifier-labelled trajectories can move boundary information into learning. The information need not be written as logic. Scale simply cannot learn from evidence the system never receives.

Behavioural reliability is not logical guarantee

A capable model may behave as though it knows a constraint, which can be strong operational evidence. Reliability is measured over cases and a distribution; a proof quantifies over a formal state space and inherits that formalisation’s assumptions.

A learned rule can be more accurate than a written rule, while a written checker can still provide a stronger claim over the small region it represents correctly. The architecture should preserve both facts instead of turning one into a verdict on the other.

The counterexample learning must receive

A weak neuro-symbolic argument says neural networks cannot be systematic and therefore need an external symbolic engine. The evidence no longer supports that categorical claim. Early results on SCAN showed recurrent sequence models succeeding when test commands resembled training combinations but failing badly when a new primitive had to compose systematically with known operators.4 That result made a genuine failure visible, but it did not establish an architectural impossibility.

Meta-learning for compositionality later trained an ordinary neural architecture across a distribution of compositional tasks. On the studied human experiments and benchmarks, it combined flexibility with systematic generalisation better than both rigid symbolic models and conventional neural baselines.5 The systematic bias was induced by the training distribution rather than installed as a symbolic module.

This is a serious negative control for the paper’s preferred design. Symbolic machinery is not a necessary condition for learned systematicity. A capability that looks absent under one objective may appear when the data and meta-objective reward it. The bitter lesson is alive inside the compositionality debate.

The same study also marks its boundary. The trained system did not automatically generalise to structures outside its meta-learning distribution and failed particular productivity splits. The result therefore supports a more careful claim: learning can acquire rule-like behaviour, but evidence of acquisition is tied to the training and evaluation regime. It does not turn all future combinations into certified cases.

The practical consequence is demanding. Before adding symbols, construct a learned-only baseline with the right data, objective, search and compute. Before removing symbols, construct a shift set in which rare or novel combinations matter. Neuro-symbolic value exists only in the difference between those matched systems.

Part III

The neuro-symbolic reply without nostalgia

The useful reply to the bitter lesson is not to rebuild a large expert system beside a neural model. It is to identify the smallest interface at which explicit semantics changes the experiment. Structure can enter at three different depths, and each supports a different claim.

Structure as loss

Compile a logical or relational regularity into the training objective. The model is encouraged to satisfy it, but runtime outputs remain statistical.

Structure as search

Let learning propose predicates, constructions or branches while a symbolic process expands consequences and prunes impossible paths.

Structure as verifier

Place a proof kernel, type checker or action guard after proposal. It accepts only candidates satisfying the formal contract.

Semantic loss compiles propositional constraints into a differentiable objective.6 DeepProbLog places neural predicates inside probabilistic logic programs.7 Neural Logic Machines use differentiable logical operators and report generalisation from smaller to larger synthetic tasks.8

These approaches can improve sample efficiency or compositional transfer. They do not all provide the same runtime guarantee. A logic-shaped loss may reduce violations without eliminating them. A probabilistic logic program can preserve interpretable dependencies while still depending on uncertain neural predicates. The words “symbolic” and “neuro-symbolic” therefore say too little about the operating claim.

Geometry shows the complementarity more clearly

AlphaGeometry used a language model to propose auxiliary constructions and a symbolic engine to close their consequences. The model ranked branches; the engine handled exact derivation. On its thirty-problem set, the system solved twenty-five.9

The result is impressive, but the ablations and later comparisons are more informative than the label. A re-evaluation found that a stronger fully symbolic combination solved twenty-one of the thirty problems on modest hardware, and that Wu’s method solved two problems missed by AlphaGeometry. Combining the methods reached twenty-seven.10 The conclusion is not that the hybrid was unnecessary. It is that each component needs a credible independent baseline.

Representation remained a bottleneck. AlphaGeometry2 expanded language coverage from 66 to 88 per cent on the reported 2000–2024 geometry set; combined improvements raised the overall solve rate to 84 per cent.11 Engineering the structure remained part of the research burden.

AlphaProof makes the relationship even starker. Reinforcement learning and large-scale search operate inside Lean, while Lean’s kernel checks the generated proof term. The system learned from millions of formalised problems and used multi-day test-time reinforcement learning on difficult competition questions. The kernel did not invent the proof. It made successful completion mechanically verifiable within the formal system.12

The checker is not the solver, and the solver is not the checker. Learning supplies a distribution over promising proof actions. Search converts that distribution into exploration. The proof assistant supplies exact state transitions and a terminal validity test. Removing the learner makes the search combinatorial. Removing the kernel makes correctness an empirical judgement about generated text.

TongGeometry continues the pattern: fine-tuned models guide symbolic exploration, with strong results on IMO-AG-30 and explicit representational limits.13 The frontier uses scale to search inside verifiable environments.

Figure 4. Structure can shape learning, search or release

Three neuro-symbolic depths Three curved channels show symbolic structure entering as a training loss, as a search operator, or as a final verifier, with guarantee strength increasing and expressive scope narrowing. Training-time regularity Search-time consequence Release-time verification wide scope • soft claim structured exploration narrow scope • hard claim guarantee strength
Conceptual taxonomy. “Soft” and “hard” describe the claim supported by the mechanism, not the quality of the system. A runtime verifier supports a hard claim only over the formal state, rule and enforcement path it actually covers.

Figure 5. In formal mathematics, learning supplies branches and the kernel supplies validity

Neural proposal and symbolic verification loop A spiral alternates between neural proposals, symbolic state expansion and search. A narrow proof kernel accepts the final proof term, while translation and library coverage remain outside the guarantee. neuralproposal symbolicclosure searchbudget proof kernel accept / reject Outside the proof claim: translation, library coverage, intended meaning
Mechanism synthesis based on AlphaGeometry-style guided deduction and AlphaProof-style kernel verification. The topology is sourced; the composition is authored. The verifier establishes formal validity, not the faithfulness of problem translation or completeness of the formal library.

The proposal-admissibility split

The general architecture can be stated without committing to a particular neural or symbolic technology. Let a learned model and search process assign an expected utility Uθ(a | x) to candidate action a, given context x. Let a set of explicit predicates Ci inspect authoritative state s, policy version p and the typed action. The selected action is:

a* = arg maxa ∈ A(s,p) Uθ(a | x),   where   A(s,p) = { a : ∧i Ci(s,p,a) = true } θ denotes learned parameters. A(s,p) is the admissible action set. Better learning changes the ranking inside the set; changed state or policy changes the set itself.

This formulation protects the bitter lesson. The model remains free to discover representations, plans and preferences. No human supplies the ranking. The constraint layer says only which proposals may cross the boundary. It can return reasons, request missing evidence or abstain when no candidate is admissible.

The split is strongest when the constraint is local. “A transfer above this amount requires two independent approvals” can be evaluated over a typed request and current approval state. “Always act in the customer’s best interest” cannot be reduced honestly to one Boolean predicate. The latter needs evidence, modelling, human judgement and contestability, not a decorative rule engine.

Explicit structure should be placed at the narrowest boundary where its inputs, semantics, owner and test oracle are all visible. Moving it deeper into the model makes enforcement harder to inspect. Expanding it into a complete world model recreates the brittleness the bitter lesson warns against.

The guarantee ends sooner than most diagrams admit

A checker evaluates a formula over represented inputs. Its guarantee is conditional on five things: the rule is correct; the representation is complete enough; the state is current; the candidate action has the semantics assumed by the checker, and no execution path bypasses enforcement. Violate any one and the system can be formally clean yet operationally wrong.

A proof assistant can verify a theorem that was mistranslated. A policy engine can approve an action against a stale entitlement snapshot. A schema can validate a payload whose identifier refers to the wrong customer. A tool can return “accepted” while the external effect remains unknown. Symbolic certainty over the wrong state is false assurance with excellent formatting.

Safe reinforcement learning through shielding makes the intended separation explicit: a learner optimises reward while a synthesised shield enforces temporal-logic properties before or after the proposed action.14 The approach is attractive because the safety analysis can be partly agnostic to the learner. Its own limitation is equally important: the shield requires a suitable abstraction of environment state and an accurate specification.

Figure 6. A verifier is only as sound as its rule-state boundary

Failure surface for explicit constraints A two-dimensional surface plots rule completeness against state fidelity. Only the high-high corner supports strong assurance; incomplete rules or stale state produce false confidence. bounded assurance complete state, wrong rule right rule, stale state test and monitor rule completeness → state fidelity →
Illustrative failure surface. No empirical percentages are implied. The strong-assurance region requires both an adequate rule and faithful current state, plus an enforced path from check to effect.
Part IV

Build the split and test it

Minimal worked example: six release actions

A model proposes six ways to complete a synthetic work order. Its score estimates benefit after latency and uncertainty. Three exact conditions apply: a hazardous job needs a permit; an irreversible action needs dual control, and the evidence snapshot must be no more than thirty days old.

CandidateModel scorePermitDual controlEvidence ageAdmissible?
A8.8Missing, requiredPresent4 daysNo
B8.4PresentPresent9 daysYes
C7.9PresentMissing, required7 daysNo
D7.5Not requiredPresent42 daysNo
E7.1PresentPresent12 daysYes
F6.4Not requiredPresent2 daysYes

The model-only system selects A. A rule-only system can avoid the invalid actions but may choose poorly among B, E and F if its preference function is crude. The hybrid removes A, C and D, then preserves the model’s learned ranking among the valid candidates and selects B. The constraint contributes no strategic intelligence; the model contributes no authority to waive the constraint.

Production-shaped worked scenario: an evidence-bound refund

An assistant receives a request to investigate and, where permitted, prepare a refund for an apparent duplicate payment. A language model can assemble evidence, distinguish plausible causes and propose the next action. The action kernel should not infer authority from the fluency of that proposal. The control system needs ten separate objects:

ObjectRole in the scenarioMechanism
IntentResolve a claimed duplicate payment for a stated purposeTyped request plus human-visible confirmation
IdentityBind customer, operator, assistant and executing serviceAuthenticated principals, never inferred from prose
World stateCurrent payment status, prior refund and destination stateAuthoritative reads with version or timestamp
ContextApplicable evidence and policy for this caseEntitled, source-linked context compilation
ReasoningGenerate hypotheses, compare records and propose an amountLearned model, retrieval and deterministic calculation
AuthorityDecide whether this principal may request this effect nowPolicy decision over identity, purpose, amount and state
ActionSubmit one idempotent refund requestTyped action contract with preconditions
EvidenceRecord what supported the proposal and policy decisionDecision receipt with source and rule versions
OutcomeEstablish whether the intended refund occurred exactly onceEffect receipt and independent readback
Release and recoveryHandle timeout, unknown outcome, rejection or compensationCheckpoint, retry discipline and escalation

The symbolic contribution is deliberately small. It does not encode how to recognise every duplicate-payment pattern. It enforces preconditions such as a verified destination, amount bounds, current entitlement and duplicate prevention. A deterministic calculation establishes the amount. The model remains useful because the evidence is messy, the hypotheses vary and the explanation must fit the case.

If policy is ambiguous, the kernel should not manufacture precision. It can route to a qualified reviewer with the assembled evidence. Bounded autonomy includes a typed refusal to act when no machine-checkable authority exists.

Figure 7. Candidate actions pass through a stateful aperture before effect

Proposal-admissibility system flow Multiple model-proposed candidate actions are ranked, checked against identity, world state, policy and evidence, then one typed action is executed and independently read back. A B C D learned ranking identity state policy evidence freshness typed effect exactly once effect receipt + readback Rejected proposals return reasons or request more evidence. Proposal is stochastic; authority and outcome evidence remain explicit.
Production-shaped architecture synthesis. No deployment numbers are implied. The routed topology is decision-relevant because authority sits between proposal and effect, while readback establishes the business outcome after execution.

A hybrid benchmark that lets learning win when it can

The accompanying Python benchmark isolates the paper’s mechanism. Each synthetic case contains six candidate release actions. Every model-led system receives the same noisy proposal score. Three observable hazards make an action invalid: a required permit is missing, an irreversible action lacks dual control, or evidence is older than thirty days.

The empirical guard is deliberately favoured: each correct hazard flag is already present, and one labelled violation teaches the whole flag. Training exceptions occur at 0.1 per cent; test exceptions shift to 15 per cent. Sixty seeds each evaluate 1,500 cases, giving 90,000 decisions per system.

Four baselines make the result discriminating: unguarded proposal; correct rules with coarse ranking; the exact hybrid, and a negative control whose freshness limit is twenty days rather than thirty.

SystemTraining actionsMedian hazards learnedViolation rateMean realised utilityCoverage
Empirical guard2500 of 314.933% [10.667, 15.880]2.974 [2.777, 3.637]100%
Empirical guard2,5002 of 35.733% [0, 11.813]4.412 [3.452, 5.335]100%
Empirical guard25,0003 of 30% [0, 0]5.311 [5.264, 5.364]100%
Unguarded proposal0015.167% [14.067, 16.133]2.925 [2.741, 3.115]100%
Rule-only030% [0, 0]4.947 [4.894, 4.996]100%
Exact hybrid030% [0, 0]5.311 [5.264, 5.364]100%
Wrong-rule hybrid03 plus false restriction0% [0, 0]4.505 [4.429, 4.566]99.333%

Intervals are the tenth to ninetieth percentiles across seeds. Invalid selections receive a synthetic utility of −12; abstentions receive zero. These numbers do not estimate a real operational rate. They demonstrate the causal trade: what changes when only the admissibility mechanism changes.

At 250 training actions, the median run sees no exception and behaves like the unguarded model. At 2,500 it sees three exceptions and learns two hazards, with wide seed variation. At 25,000 it learns all three and matches the exact hybrid.

The benchmark does not say learning fails. It shows learning succeeding once the relevant evidence arrives, while making the cost of waiting for that evidence visible. This is the bitter lesson in its strongest form. Enough data eliminates the performance gap in this favourable finite setting.

The other baselines prevent a symbolic victory lap. Rule-only control removes violations but loses utility. The exact hybrid combines the stronger ranking and correct boundary. The wrong rule also records zero violations, yet lowers utility to 4.505, changes 33.6 per cent of choices and sometimes abstains. A bad rule can look safest on its own metric.

Figure 8. Rare observations determine whether the empirical guard finds the boundary

Synthetic benchmark violation rates Bars show median invalid selections. The empirical guard falls from 14.933 per cent at 250 training actions to 5.733 per cent at 2,500 and zero at 25,000. Exact constraints, rule-only and wrong-rule systems have zero measured violations. 0 4 8 12 16% 14.933%5.733%0%15.167%0%0% 250train 2,500train 25,000train unguarded rule-only exacthybrid Median invalid selections across 1,500 decisions per seed
Measured synthetic result: 60 seeds, 1,500 cases per seed, six candidates per case. Bars show medians. The full table reports tenth to ninetieth percentile intervals. Zero means no violation occurred in the benchmark, not a universal guarantee.

Figure 9. Zero violations can hide either good control or a bad rule

Synthetic utility comparison A utility chart shows exact hybrid at 5.311, rule-only at 4.947, wrong-rule hybrid at 4.505 and unguarded at 2.925. A separate coral marker notes that the wrong rule changes 33.6 per cent of choices despite zero violations. 2.53.54.55.5 5.3114.9474.5052.925 exacthybridrule-onlywrong-rulehybridunguarded wrong rule changes 33.6% of exact-hybrid choices Median realised utility; synthetic scale, invalid action penalty = −12
Measured synthetic result over the same 90,000 decisions per system. Utility has no real-world unit. The negative control demonstrates why violation rate must be paired with coverage, false restriction, utility and rule mutation tests.

The executable artefact

The program uses only Python’s standard library. Run it with python paper16_hybrid_benchmark.py. The seed family, exception rates, candidate count, invalid-action penalty and evaluation population are declared at the top. Expected output is the table above plus the analytic encounter count for a 0.1 per cent exception.

Open the complete runnable benchmark
#!/usr/bin/env python3
"""A synthetic benchmark for the proposal-admissibility split.

The benchmark gives learning an unusually favourable task: every hard failure is
already represented by one of three observable hazard flags. The empirical guard
only has to observe a hazard once to learn that it must be blocked. The hybrid
system receives the three exact constraints directly. All systems use synthetic
data and a fixed family of random seeds.
"""

from __future__ import annotations

from dataclasses import dataclass
import math
import random
from statistics import mean, median
from typing import Callable, Iterable

BASE_SEED = 16016
REPLICATES = 60
TRAIN_EXCEPTION_RATE = 0.001  # 0.1% of training actions
TEST_EXCEPTION_RATE = 0.15    # shifted test: 15% of candidate actions
TEST_CASES = 1_500
CANDIDATES_PER_CASE = 6
INVALID_PENALTY = -12.0


@dataclass(frozen=True)
class Action:
    gain: float
    latency: float
    uncertainty: float
    requires_permit: bool
    permit_present: bool
    irreversible: bool
    dual_control: bool
    evidence_age_days: float
    proposal_score: float


def hazards(action: Action, freshness_limit: float = 30.0) -> frozenset[str]:
    found: set[str] = set()
    if action.requires_permit and not action.permit_present:
        found.add("missing_permit")
    if action.irreversible and not action.dual_control:
        found.add("missing_dual_control")
    if action.evidence_age_days > freshness_limit:
        found.add("stale_evidence")
    return frozenset(found)


def is_valid(action: Action) -> bool:
    return not hazards(action)


def true_utility(action: Action) -> float:
    """Synthetic utility before admissibility is considered."""
    return (
        8.0 * action.gain
        - 2.5 * action.latency
        - 2.0 * action.uncertainty
        + 1.5 * action.gain * (1.0 - action.uncertainty)
    )


def generate_action(rng: random.Random, exception_rate: float) -> Action:
    gain = rng.random()
    latency = rng.random()
    uncertainty = rng.random()
    requires_permit = rng.random() < 0.35
    irreversible = rng.random() < 0.20

    # Safe by construction unless one exceptional condition is injected.
    permit_present = True
    dual_control = True
    evidence_age_days = rng.uniform(0.0, 30.0)

    if rng.random() < exception_rate:
        kind = rng.choice(("permit", "dual", "stale"))
        if kind == "permit":
            requires_permit = True
            permit_present = False
        elif kind == "dual":
            irreversible = True
            dual_control = False
        else:
            evidence_age_days = rng.uniform(30.01, 60.0)

    provisional = Action(
        gain=gain,
        latency=latency,
        uncertainty=uncertainty,
        requires_permit=requires_permit,
        permit_present=permit_present,
        irreversible=irreversible,
        dual_control=dual_control,
        evidence_age_days=evidence_age_days,
        proposal_score=0.0,
    )
    return Action(
        **{
            **provisional.__dict__,
            # Same noisy learned proposal signal for every model-led system.
            "proposal_score": true_utility(provisional) + rng.gauss(0.0, 0.45),
        }
    )


def build_cases(
    rng: random.Random,
    n_cases: int = TEST_CASES,
    candidates: int = CANDIDATES_PER_CASE,
    exception_rate: float = TEST_EXCEPTION_RATE,
) -> list[list[Action]]:
    cases: list[list[Action]] = []
    for _ in range(n_cases):
        case = [generate_action(rng, exception_rate) for _ in range(candidates)]
        if not any(is_valid(action) for action in case):
            case[0] = generate_action(rng, 0.0)
        cases.append(case)
    return cases


def learn_hazards(training: Iterable[Action]) -> frozenset[str]:
    """Optimistic empirical learner: one labelled failure teaches a whole flag."""
    learned: set[str] = set()
    for action in training:
        if not is_valid(action):
            learned.update(hazards(action))
    return frozenset(learned)


def best(case: list[Action], eligible: Callable[[Action], bool], score) -> Action | None:
    allowed = [action for action in case if eligible(action)]
    return max(allowed, key=score, default=None)


def choose_unguarded(case: list[Action]) -> Action | None:
    return best(case, lambda _: True, lambda action: action.proposal_score)


def choose_empirical(case: list[Action], learned: frozenset[str]) -> Action | None:
    return best(
        case,
        lambda action: hazards(action).isdisjoint(learned),
        lambda action: action.proposal_score,
    )


def choose_rule_only(case: list[Action]) -> Action | None:
    # Exact admissibility, but a deliberately coarse hand-written preference.
    return best(
        case,
        is_valid,
        lambda action: 5.0 * action.gain - 4.0 * action.latency,
    )


def choose_hybrid(case: list[Action]) -> Action | None:
    return best(case, is_valid, lambda action: action.proposal_score)


def choose_wrong_rule(case: list[Action]) -> Action | None:
    # Negative control: the explicit rule says 20 days, but truth says 30 days.
    return best(
        case,
        lambda action: not hazards(action, freshness_limit=20.0),
        lambda action: action.proposal_score,
    )


def evaluate(cases: list[list[Action]], chooser: Callable[[list[Action]], Action | None]) -> dict[str, float]:
    realised: list[float] = []
    violations = 0
    abstentions = 0
    changed_from_exact = 0

    for case in cases:
        selected = chooser(case)
        exact = choose_hybrid(case)
        if selected is None:
            abstentions += 1
            realised.append(0.0)
        elif not is_valid(selected):
            violations += 1
            realised.append(INVALID_PENALTY)
        else:
            realised.append(true_utility(selected))

        if selected != exact:
            changed_from_exact += 1

    n = len(cases)
    return {
        "coverage_pct": 100.0 * (n - abstentions) / n,
        "violation_pct": 100.0 * violations / n,
        "mean_realised_utility": mean(realised),
        "changed_from_exact_pct": 100.0 * changed_from_exact / n,
    }


def percentile(values: list[float], q: float) -> float:
    ordered = sorted(values)
    position = (len(ordered) - 1) * q
    lower = math.floor(position)
    upper = math.ceil(position)
    if lower == upper:
        return ordered[lower]
    fraction = position - lower
    return ordered[lower] * (1.0 - fraction) + ordered[upper] * fraction


def summarise(rows: list[dict[str, float]], key: str) -> tuple[float, float, float]:
    values = [row[key] for row in rows]
    return median(values), percentile(values, 0.10), percentile(values, 0.90)


def run() -> None:
    training_sizes = (250, 2_500, 25_000)
    results: dict[str, list[dict[str, float]]] = {
        f"empirical_{size}": [] for size in training_sizes
    }
    for name in ("unguarded", "rule_only", "hybrid_exact", "hybrid_wrong_rule"):
        results[name] = []

    learned_counts: dict[int, list[int]] = {size: [] for size in training_sizes}
    observed_exceptions: dict[int, list[int]] = {size: [] for size in training_sizes}

    for replicate in range(REPLICATES):
        rng = random.Random(BASE_SEED + replicate)
        cases = build_cases(rng)

        for size in training_sizes:
            training = [generate_action(rng, TRAIN_EXCEPTION_RATE) for _ in range(size)]
            learned = learn_hazards(training)
            learned_counts[size].append(len(learned))
            observed_exceptions[size].append(sum(not is_valid(action) for action in training))
            results[f"empirical_{size}"].append(
                evaluate(cases, lambda case, learned=learned: choose_empirical(case, learned))
            )

        results["unguarded"].append(evaluate(cases, choose_unguarded))
        results["rule_only"].append(evaluate(cases, choose_rule_only))
        results["hybrid_exact"].append(evaluate(cases, choose_hybrid))
        results["hybrid_wrong_rule"].append(evaluate(cases, choose_wrong_rule))

    print("Synthetic proposal-admissibility benchmark")
    print(
        f"replicates={REPLICATES}; test_cases/replicate={TEST_CASES}; "
        f"candidates/case={CANDIDATES_PER_CASE}"
    )
    print(
        f"training exceptions={100 * TRAIN_EXCEPTION_RATE:.1f}%; "
        f"shifted test exceptions={100 * TEST_EXCEPTION_RATE:.0f}%"
    )
    print("Intervals are 10th to 90th percentiles across random seeds.")
    print()
    print(
        "system,train_actions,observed_exceptions_median,learned_hazards_median,"
        "violation_pct_median,violation_pct_p10,violation_pct_p90,"
        "utility_median,utility_p10,utility_p90,coverage_pct_median,"
        "changed_from_exact_pct_median"
    )

    order = [f"empirical_{size}" for size in training_sizes] + [
        "unguarded",
        "rule_only",
        "hybrid_exact",
        "hybrid_wrong_rule",
    ]
    for name in order:
        rows = results[name]
        violation = summarise(rows, "violation_pct")
        utility = summarise(rows, "mean_realised_utility")
        coverage = summarise(rows, "coverage_pct")
        changed = summarise(rows, "changed_from_exact_pct")
        if name.startswith("empirical_"):
            size = int(name.split("_")[1])
            observed = median(observed_exceptions[size])
            learned = median(learned_counts[size])
        else:
            size = 0
            observed = 0
            learned = 0
        print(
            f"{name},{size},{observed:.1f},{learned:.1f},"
            f"{violation[0]:.3f},{violation[1]:.3f},{violation[2]:.3f},"
            f"{utility[0]:.3f},{utility[1]:.3f},{utility[2]:.3f},"
            f"{coverage[0]:.3f},{changed[0]:.3f}"
        )

    # A transparent analytic check on the rare-event mechanism.
    for confidence in (0.95, 0.99):
        n = math.log(1.0 - confidence) / math.log(1.0 - TRAIN_EXCEPTION_RATE)
        print(
            f"actions for {100 * confidence:.0f}% chance of seeing at least one "
            f"0.1% exception: {math.ceil(n):,}"
        )


if __name__ == "__main__":
    run()
Open the recorded output from the release run
Synthetic proposal-admissibility benchmark
replicates=60; test_cases/replicate=1500; candidates/case=6
training exceptions=0.1%; shifted test exceptions=15%
Intervals are 10th to 90th percentiles across random seeds.

system,train_actions,observed_exceptions_median,learned_hazards_median,violation_pct_median,violation_pct_p10,violation_pct_p90,utility_median,utility_p10,utility_p90,coverage_pct_median,changed_from_exact_pct_median
empirical_250,250,0.0,0.0,14.933,10.667,15.880,2.974,2.777,3.637,100.000,14.933
empirical_2500,2500,3.0,2.0,5.733,0.000,11.813,4.412,3.452,5.335,100.000,5.733
empirical_25000,25000,25.0,3.0,0.000,0.000,0.000,5.311,5.264,5.364,100.000,0.000
unguarded,0,0.0,0.0,15.167,14.067,16.133,2.925,2.741,3.115,100.000,15.167
rule_only,0,0.0,0.0,0.000,0.000,0.000,4.947,4.894,4.996,100.000,33.500
hybrid_exact,0,0.0,0.0,0.000,0.000,0.000,5.311,5.264,5.364,100.000,0.000
hybrid_wrong_rule,0,0.0,0.0,0.000,0.000,0.000,4.505,4.429,4.566,99.333,33.600
actions for 95% chance of seeing at least one 0.1% exception: 2,995
actions for 99% chance of seeing at least one 0.1% exception: 4,603

A placement decision instrument

A team should not begin with “we need neuro-symbolic AI”. It should begin with a candidate proposition and try to earn the right to enforce it. The following test turns the philosophical dispute into an architecture decision.

Constraint locality test

  1. Precision: Can two qualified people state the condition so that independent implementations agree on ordinary and edge cases?
  2. Observability: Are the required inputs available from authoritative, fresh and identity-bound state before the action?
  3. Consequence: Is violation materially harmful, difficult to reverse or unacceptable during exploration?
  4. Rarity: Would representative data contain enough violations and combinations to learn and evaluate the boundary?
  5. Ownership: Does the rule have an accountable owner, effective time, version and withdrawal path?
  6. Local enforceability: Can the condition be checked at one typed interface without modelling the whole world?
  7. Independent outcome evidence: Can the system verify the postcondition and distinguish rejection, success and unknown outcome?

High scores on precision, consequence, ownership and local enforceability favour an explicit runtime guard. Low precision favours learned judgement or human review. Weak observability blocks a hard guarantee even when the policy is crisp. Low consequence and abundant feedback favour learning, because adaptation may matter more than zero empirical violations.

Figure 10. Place structure by exactness and consequence, then test state fidelity

Constraint placement matrix A two-by-two field maps low to high rule exactness against low to high violation consequence. Learned judgement occupies the low-low region, soft structured loss the high-exactness low-consequence region, human review the low-exactness high-consequence region, and runtime guard or proof checker the high-high region. Learn and monitor common • reversible • fuzzy Structured loss regularity, not a guarantee Human judgement consequential but ambiguous Runtime guard or proof checker exact • observable • owned rule exactness → violation consequence → only if state fidelity is high
Practitioner decision instrument. Axes are ordinal, not measured scales. The coral qualification is decisive: crisp policy without reliable current state belongs in review or evidence acquisition, not in a falsely “hard” guard.

Choose the weakest sufficient form of structure

ConditionPreferred mechanismRelease evidenceFailure test
Fuzzy preference, frequent feedback, reversible actionLearned model with calibration and monitoringRepresentative evaluation and live outcome slicesDistribution shift and subgroup regression
Known regularity that improves data efficiencyStructured features, architecture or semantic lossAblation against a matched learned-only baselineConstraint removal and incorrect-constraint control
Large branching space with exact transitionsLearned heuristic plus symbolic or simulated searchSolve rate, search cost and independent verifierHeuristic-only and symbolic-only baselines
Crisp precondition before a consequential effectRuntime shield or deterministic authority kernelProperty tests, policy version and decision receiptStale state, bypass, race and mutation tests
Formal object with machine-checkable semanticsProof assistant, type checker or certified solverChecked proof term plus translation provenanceMistranslation and library-coverage challenge
High consequence but irreducibly ambiguous judgementEvidence assembly and accountable human decisionContestable rationale, sources and decision rightsDisagreement, missing evidence and escalation drill

The experiment should then compare at least three systems under matched proposal compute: learned-only, structure-only and hybrid. Test ordinary data, rare exceptions and distribution shift. Report useful outcome, violation rate, coverage, abstention, latency and total cost. Mutate or age the rule state so that an incorrect constraint cannot win merely by defining its own success metric.

This final step prevents architectural branding. A hybrid earns its complexity only if it reduces a consequential failure or evaluation burden without an unacceptable loss of coverage, utility or adaptability. A learned-only system earns removal of the guard only if fresh evidence shows that the residual risk and recovery path are acceptable. The decision is empirical, but the evidence required depends on the kind of claim being made.

What would overturn the placement

The placement rule is falsifiable. Freeze the proposal model, candidate set, compute budget and outcome evaluator. Then compare learned-only, structure-only and hybrid systems across ordinary cases, deliberately rare combinations, shifted frequencies, stale state and mutated rules. Record useful outcome, material violations, abstention, coverage, latency, review burden and recovery cost. Run the explicit check in shadow mode before giving it authority, so false restrictions become visible without blocking valid work. The guard earns release only when its reduction in consequential error survives this matched comparison and remains larger than the cost of maintaining its rule and state dependencies.

Evidence should count against the guard when a learned system reaches the same bounded violation rate and recovery performance under the relevant shifts, while adapting faster or preserving materially more utility. It should also count against the guard when specification disagreements, stale inputs or bypass paths cause more harm than the boundary prevents. In that case, retire the rule, reduce it to an advisory signal or route the ambiguous proposition to human judgement. Conversely, zero observed violations is never sufficient on its own. Report the evaluation denominator, uncertainty, injected failure coverage and the cases the checker could not represent. The decision is not whether symbols feel reassuring. It is whether the constrained interface improves outcomes under tests capable of making it lose.

Two adjacent articles delimit the neighbouring questions: What Scaling Laws Don’t Tell You covers capability and economics, while The Certainty Gradient covers mechanism placement. This paper supplies the causal boundary.

Compact glossary

Admissibility
Whether a candidate action satisfies the explicit preconditions required for release in the current state.
Inductive structure
An architectural or training bias that makes some functions easier to learn without directly encoding a full solution.
Neuro-symbolic system
A system in which learned numerical components interact materially with symbolic representations, inference, constraints or verification.
Shield
A mechanism that filters or corrects a learner’s proposed actions to enforce a stated safety property.
Proof kernel
A small trusted checker that verifies whether a formal proof term follows the rules of a formal system.

Source ledger

Official and foundational

  1. Richard S. Sutton, “The Bitter Lesson”. Official essay stating the historical case for general methods that scale through search and learning.

Primary research

  1. David Silver et al., “A general reinforcement learning algorithm that masters chess, shogi, and Go through self-play”. AlphaZero mechanism and results.
  2. Julian Schrittwieser et al., “Mastering Atari, Go, Chess and Shogi by Planning with a Learned Model”. MuZero’s learned planning model and search-scaling limits.
  3. Brenden M. Lake and Marco Baroni, “Generalization without systematicity”. SCAN benchmark and early neural compositionality failure.
  4. Brenden M. Lake and Marco Baroni, “Human-like systematic generalization through a meta-learning neural network”. Counterevidence showing systematicity induced through meta-learning, with stated out-of-distribution limits.
  5. Jingyi Xu et al., “A Semantic Loss Function for Deep Learning with Symbolic Knowledge”. Logical constraints compiled into a differentiable training loss.
  6. Robin Manhaeve et al., “DeepProbLog: Neural Probabilistic Logic Programming”. Neural predicates integrated with probabilistic logic.
  7. Honghua Dong et al., “Neural Logic Machines”. Differentiable relational and logical operators with scale generalisation on synthetic tasks.
  8. Trieu H. Trinh et al., “Solving olympiad geometry without human demonstrations”. AlphaGeometry’s learned construction proposals and symbolic deduction engine.
  9. Shiven Sinha et al., “Wu’s Method can Boost Symbolic AI to Rival Silver Medalists and AlphaGeometry to Outperform Gold Medalists at IMO Geometry”. Stronger symbolic baseline and complementary failures.
  10. Yuri Chervonyi et al., “Gold-medalist Performance in Solving Olympiad Geometry with AlphaGeometry2”. Expanded representation coverage and improved hybrid search.
  11. Thomas Hubert et al., “Olympiad-level formal mathematical reasoning with reinforcement learning”. AlphaProof’s large-scale RL, test-time adaptation and Lean-kernel verification.
  12. Chi Zhang et al., “Proposing and solving olympiad geometry with guided tree search”. TongGeometry’s guided symbolic search and bounded representation.
  13. Mohammed Alshiekh et al., “Safe Reinforcement Learning via Shielding”. Temporal-logic shields separating optimisation from enforced safety.

Design inference

  • The proposal-admissibility split, constraint locality test, production-shaped scenario and benchmark are authored synthesis. Their status is an engineering judgement and a falsifiable experimental proposal, not a published universal result.
  • The two related articles are used only to delimit adjacent questions on scaling evidence and deterministic mechanism placement.

Let scale search; make every boundary earn its place

The bitter lesson remains one of the best correctives in artificial intelligence. Human designers repeatedly mistake their convenient decomposition for the structure of the problem. When data, search and compute can keep improving a method, a hand-built strategic rule is usually a temporary advantage and eventually a constraint.

The neuro-symbolic reply survives only after accepting that lesson. It should not preserve expert knowledge because the knowledge feels meaningful. It should preserve a proposition only when the proposition is exact, consequential, observable and cheaper to verify than to relearn through failure. Even then, the rule needs an owner, a version, current state, a bypass-resistant enforcement point and a negative control that reveals over-restriction.

The strongest current systems in formal reasoning demonstrate the pattern. Learning and search generate possibilities at a scale that hand-written heuristics cannot match. Symbolic environments turn success into a crisp feedback signal and proof kernels verify the result. Neither component licenses the elimination of the other. Each removes a different uncertainty.

The architecture decision changes from “neural or symbolic?” to “which uncertainty belongs to learning, which proposition can be checked, and what evidence connects the check to the real outcome?” Default to learning for perception, strategy, ranking and adaptation. Add explicit structure only at a narrow boundary with a discriminating ablation. Remove it when a matched learned system earns the same outcome and risk evidence. Keep it when rare, irreversible exceptions make empirical rediscovery the more expensive form of intelligence.