Candidate — hypothesis, не accepted layout
8.03 выдаёт bounded horizontal hypotheses поверх уже существующей сетки. Он не двигает content и не создаёт полный 2D layout.
One explicit contentRef.
Explicit raw/accepted budgets.
Seed priority is sampling only.
Все степени свободы explicit
Нет встроенного «поставить по центру» или «попробовать все spans». Source choices приходят в request.
ColumnPlacementRequest {
requestRef,
contentRef,
gridRef,
columnGeometryRef,
topologyRef,
occupancyRegistryRef?,
placementMode,
allowedSpanRefs[]?
allowedNodeRefs[]?
boundaryBindingSides?
bindingKind?
occupancyPolicy,
diversityPolicy,
generationBudget,
seed,
confidence,
provenance
}
Сначала считаем размер пространства
Если request сам задаёт слишком большое пространство, это ошибка планирования запроса, а не повод незаметно взять первые N вариантов.
GenerationBudget {
maxRawEvaluations,
maxAcceptedCandidates
}
Три baseline X-hypothesis
Каждый mode имеет один owner-qualified source.
SPAN_INTERVAL
Берёт x0/x1 из одного resolved contiguous span.
NODE_ANCHOR
Берёт один canonical xAnchor из GridNode.
SPAN + BINDINGS
Span interval + proposed left/right node-binding templates.
Span geometry не пересчитывается
8.03 только ссылается на 8.01 span и переносит X-constraint в candidate.
{
placementMode:
"SPAN_INTERVAL",
xConstraint:
"X_INTERVAL",
spanRef,
spanColumnCount,
x0Raw,
x1Raw,
widthRaw
}
Anchor — explicit topology identity
Использование node как anchor не является измерением alignment quality.
{
placementMode:
"NODE_ANCHOR",
xConstraint:
"X_ANCHOR",
anchorNodeRef,
xAnchorRaw
}
Registry остаётся immutable
Candidate может предложить будущие bindings, но не записывает их в 8.02.
State используется только по explicit policy
Никакой universal capacity logic внутри генератора нет.
CandidateOccupancyPolicy {
enabled,
requiredEvidence,
allowedNodeStates: [
FREE |
UNKNOWN |
OCCUPIED |
MULTI_OCCUPIED |
N_A
],
appliesTo:
PROPOSED_BINDING_NODES
}
Validate → filter → dedup → bound
Sampling происходит только после semantic validity/hard filtering.
Dedup не смешивает разные semantics
Seed не входит в semantic signature.
Deterministic sampling, не ranking
Когда eligible pool превышает accepted budget, используется reproducible seed-priority.
Representation cap без aesthetics
Diversity pruning включается только отдельным policy.
CandidateDiversityPolicy {
enabled,
family:
SPAN_COLUMN_COUNT |
PLACEMENT_MODE,
maxPerFamilyValue
}
Много объектов — независимые sets
Batch нужен для удобства orchestration, но не создаёт combinations.
Каждый candidate воспроизводим
Lineage должен быть достаточен, чтобы понять, на какой версии сетки/occupancy он был создан.
lineage {
gridRef,
columnGeometryRef,
topologyRef,
occupancyRegistryRef?,
requestRef,
seed,
sourceSpanRef?,
sourceNodeRef?
}
8.03 заканчивается до scoring
Candidate generation и candidate evaluation — разные слои.
| Question | Owner |
|---|---|
| Span geometry? | 8.01 |
| Node topology/current occupancy? | 8.02 |
| Generate bounded X hypotheses? | 8.03 |
| Choose/score grid variants? | 8.04 |
| 2D cell placement? | Topic 9+ |
| Alignment quality? | Topic 10 |
Visual Lab
Один объект, один request, bounded candidate set.
8.03 candidate regression
Проверяем budgets, три modes, occupancy states, proposed bindings, dedup, seed behavior, diversity и отсутствие cross-product/scoring.
DATA FOR LAYOUT ENGINE
Machine-readable 8.03 contract.
{
"module": "Compo 8.03",
"name": "placement_candidates",
"version": "1.1-corrective",
"canonical_main_title": "Placement candidates",
"topic": "08_КОЛОННАЯ_СЕТКА",
"scope": "BOUNDED_SEEDED_DETERMINISTIC_COLUMNGRID_X_PLACEMENT_CANDIDATE_GENERATION_WITH_LINEAGE_FILTERING_DEDUP_AND_OPTIONAL_DIVERSITY",
"consumes": [
"Compo8.00.ColumnGrid",
"Compo8.01.ResolvedColumnGeometry",
"Compo8.01.ResolvedColumnSpan[]",
"Compo8.02.ColumnGridTopology",
"optional Compo8.02.ColumnGridNodeOccupancyRegistry",
"explicit ColumnPlacementRequest"
],
"provides": [
"ColumnPlacementRequest",
"GenerationBudget",
"CandidateOccupancyPolicy",
"CandidateDiversityPolicy",
"ColumnPlacementCandidate",
"CandidateRejectionDiagnostic",
"ColumnPlacementCandidateSet",
"PlacementCandidateBatchResult",
"candidateSetRef for Compo8.04"
],
"owns_metrics": [],
"descriptors_only": [
"grid.placement.mode",
"grid.placement.spanRef",
"grid.placement.spanColumnCount",
"grid.placement.x0Raw",
"grid.placement.x1Raw",
"grid.placement.xAnchorRaw",
"grid.placement.anchorNodeRef",
"grid.placement.proposedNodeBindingRefs",
"grid.placement.signature",
"grid.placement.seedPriority",
"grid.placement.filterStatus",
"grid.placement.rejectionReason"
],
"generation_budget_schema": {
"maxRawEvaluations": "integer >=1; hard cap on potential search-space cardinality",
"maxAcceptedCandidates": "integer >=1 and <= maxRawEvaluations",
"important": "space larger than maxRawEvaluations returns BUDGET_EXCEEDED; no silent prefix truncation"
},
"occupancy_policy_schema": {
"enabled": "boolean",
"requiredEvidence": "boolean",
"allowedNodeStates": "explicit non-empty subset of FREE|UNKNOWN|OCCUPIED|MULTI_OCCUPIED|N_A when enabled",
"appliesTo": "PROPOSED_BINDING_NODES",
"important": "policy does not redefine 8.02 states and does not imply universal capacity"
},
"diversity_policy_schema": {
"enabled": "boolean",
"family": "SPAN_COLUMN_COUNT|PLACEMENT_MODE",
"maxPerFamilyValue": "integer >=1 when enabled",
"important": "deterministic representation cap only, not quality scoring"
},
"column_placement_request_schema": {
"requestRef": "stable explicit ref",
"contentRef": "owner-qualified content/object ref",
"gridRef": "same ColumnGrid",
"columnGeometryRef": "same Compo8.01 geometry",
"topologyRef": "same Compo8.02 topology",
"occupancyRegistryRef": "optional registry ref",
"placementMode": "SPAN_INTERVAL|NODE_ANCHOR|SPAN_WITH_BOUNDARY_BINDINGS",
"allowedSpanRefs": "required non-empty unique span refs for span modes",
"allowedNodeRefs": "required non-empty unique node refs for NODE_ANCHOR",
"boundaryBindingSides": "LEFT|RIGHT|BOTH for SPAN_WITH_BOUNDARY_BINDINGS",
"bindingKind": "PLACEMENT_ANCHOR|CONTENT_EDGE|CONTENT_CENTER|CUSTOM when bindings are proposed",
"occupancyPolicy": "CandidateOccupancyPolicy",
"diversityPolicy": "CandidateDiversityPolicy",
"generationBudget": "GenerationBudget",
"seed": "required deterministic string/integer token",
"confidence": "0..1",
"provenance": "object"
},
"placement_modes": {
"SPAN_INTERVAL": {
"source": "one explicit ResolvedColumnSpan",
"xConstraint": "X_INTERVAL",
"outputs": "x0Raw,x1Raw,widthRaw,spanRef",
"occupancy": "none unless another explicit mode is used"
},
"NODE_ANCHOR": {
"source": "one explicit canonical GridNode",
"xConstraint": "X_ANCHOR",
"outputs": "xAnchorRaw,anchorNodeRef",
"occupancy": "candidate may be filtered against that node via explicit occupancyPolicy; no registry mutation"
},
"SPAN_WITH_BOUNDARY_BINDINGS": {
"source": "one explicit ResolvedColumnSpan + its canonical left/right boundary nodes",
"xConstraint": "X_INTERVAL",
"outputs": "span interval + proposed NodeOccupancyBinding templates",
"occupancy": "filter proposed boundary binding nodes through explicit occupancyPolicy"
}
},
"candidate_schema": {
"candidateRef": "stable derived ref",
"candidateSetRef": "parent set ref",
"requestRef": "source request",
"contentRef": "source content",
"placementMode": "one baseline mode",
"xConstraint": "X_INTERVAL|X_ANCHOR",
"spanRef": "optional",
"spanColumnCount": "optional",
"x0Raw": "optional",
"x1Raw": "optional",
"widthRaw": "optional",
"anchorNodeRef": "optional",
"xAnchorRaw": "optional",
"proposedNodeBindings": "mutation-free binding templates",
"canonicalSignature": "semantic de-dup identity",
"seedPriority": "deterministic seed-derived integer used only for bounded subset selection",
"lineage": "grid/geometry/topology/registry/request/seed/source refs",
"status": "ELIGIBLE",
"confidence": "minimum relevant evidence confidence",
"provenance": "DERIVED",
"score": "must be absent/null"
},
"candidate_signature": {
"SPAN_INTERVAL": "mode|spanRef|x0|x1",
"NODE_ANCHOR": "mode|nodeRef|x",
"SPAN_WITH_BOUNDARY_BINDINGS": "mode|spanRef|sides|bindingKind|boundaryNodeRefs",
"important": "seed is not part of semantic signature; seed controls subset selection after eligibility"
},
"search_space_policy": {
"one_request_one_content": "mandatory",
"potentialSpace": "count of explicit allowed span/node source choices after request validation",
"budgetCheck": "potentialSpace <= maxRawEvaluations required before candidate evaluation",
"cross_content_cartesian_product": "FORBIDDEN",
"batch": "process requests independently and return per-request candidate sets"
},
"filter_pipeline": [
"validate request/lineage",
"compute potential search-space cardinality",
"enforce maxRawEvaluations",
"materialize one raw candidate per explicit allowed source choice",
"resolve proposed boundary nodes where needed",
"apply explicit occupancyPolicy",
"record rejection diagnostics",
"de-duplicate eligible candidates by canonicalSignature",
"apply explicit diversityPolicy if enabled",
"if still above maxAcceptedCandidates, select by seedPriority then canonicalSignature",
"emit canonical candidate ordinal order"
],
"occupancy_filter_semantics": {
"policy_disabled": "do not query registry for filtering",
"requiredEvidence_true_missing_registry": "candidate set N_A for modes requiring occupancy evidence",
"requiredEvidence_false_missing_registry": "candidate may remain eligible with occupancyEvidenceStatus=N_A",
"queried_node_state_not_allowed": "HARD_FILTERED candidate diagnostic",
"PARTIAL_UNKNOWN": "remains UNKNOWN and is filtered/allowed exactly according allowedNodeStates",
"registry_mutation": "FORBIDDEN"
},
"proposed_binding_semantics": {
"proposal_only": "proposedNodeBindings are not registered bindings",
"bindingRef": "derived candidate-local proposal ref",
"bindingStatus": "PROPOSED",
"targetNodeRef": "canonical node",
"contentRef": "request content",
"sourceOwnerRef": "Compo8.03",
"sourceEvidenceRef": "candidateRef",
"acceptance": "external layout/integration owner may later convert an accepted proposal into an explicit 8.02 registry binding snapshot"
},
"diversity_semantics": {
"disabled": "no diversity pruning",
"SPAN_COLUMN_COUNT": "at most maxPerFamilyValue candidates for each spanColumnCount",
"PLACEMENT_MODE": "at most maxPerFamilyValue candidates for each placementMode",
"selection_within_family": "seedPriority then canonicalSignature",
"quality": "none"
},
"ownership_map": {
"8.00": "grid root/domain",
"8.01": "column/gutter/span geometry",
"8.02": "canonical lines/nodes and current occupancy registry",
"8.03": "bounded deterministic X-placement candidates and proposed occupancy deltas",
"8.04": "grid variants, target scoring, violations/repair and consolidated Topic8 tests",
"9.x": "2D rows/cells/regions",
"10.x": "alignment/proximity evaluation"
},
"semantic_firewalls": {
"candidate_vs_layout": "candidate is a horizontal hypothesis, not accepted layout state",
"candidate_vs_registry": "proposed bindings do not mutate current occupancy",
"candidate_vs_alignment": "using a node as an explicit anchor is not a measured alignment score",
"candidate_vs_score": "seedPriority is sampling priority only, never aesthetic rank",
"span_width_vs_quality": "wider/narrower span has no built-in quality ordering",
"free_node_vs_quality": "FREE is availability evidence, not quality"
},
"metric_policy": {
"direct_scoring": "FORBIDDEN in 8.03",
"seedPriority_is_score": "FORBIDDEN",
"span_width_score": "FORBIDDEN",
"centered_candidate_score": "FORBIDDEN",
"free_node_score": "FORBIDDEN",
"beautyScore": "FORBIDDEN"
},
"hard_constraints": [
"8.03 owns bounded deterministic ColumnGrid placement-candidate generation and candidate lineage only.",
"A ColumnPlacementCandidate describes horizontal X constraints against an already resolved Topic8 grid; it is not a complete 2D layout placement.",
"8.03 does not own Y placement, object height, typography, image crop, collision resolution, balance, hierarchy or eye flow.",
"Candidate generation consumes explicit Compo8.01 geometry and Compo8.02 topology; it does not reconstruct columns, spans, lines or nodes.",
"Every placement request is for one explicit contentRef. 8.03 must not form Cartesian products across candidate sets of multiple content items.",
"Every request requires an explicit deterministic seed and explicit GenerationBudget.",
"GenerationBudget.maxRawEvaluations is a hard upper bound on the request search-space cardinality. If potential candidate count exceeds it, return BUDGET_EXCEEDED; do not silently truncate search.",
"GenerationBudget.maxAcceptedCandidates is a hard upper bound on emitted candidates after filtering/deduplication.",
"If eligible candidates exceed maxAcceptedCandidates, selection is deterministic and seed-dependent using canonical candidate signatures; the same inputs and seed must reproduce the same subset.",
"A different seed may select a different subset but must not alter validity/hard-filter semantics.",
"Baseline placement modes are SPAN_INTERVAL, NODE_ANCHOR and SPAN_WITH_BOUNDARY_BINDINGS.",
"SPAN_INTERVAL uses an explicit contiguous ColumnSpan geometry from 8.01 and emits X_INTERVAL evidence only.",
"NODE_ANCHOR uses one explicit canonical GridNode and emits X_ANCHOR evidence only.",
"SPAN_WITH_BOUNDARY_BINDINGS uses a span interval and may propose left/right node bindings; these are proposed occupancy deltas, not mutations of the 8.02 registry.",
"Proposed bindings must reference the canonical boundary nodes of the selected span.",
"8.03 never mutates ColumnGridNodeOccupancyRegistry.",
"Occupancy filtering is allowed only through explicit CandidateOccupancyPolicy.",
"If occupancy evidence is required by policy and the registry is missing/N_A/PARTIAL for a queried node, the candidate cannot be silently treated as free.",
"COMPLETE registry FREE and PARTIAL registry UNKNOWN remain distinct during candidate filtering.",
"MULTI_OCCUPIED is not intrinsically invalid; it is filtered only if the explicit allowedNodeStates policy excludes it.",
"No universal preference for wider spans, centered spans, free nodes or particular anchor kinds exists.",
"Candidate de-duplication uses a canonical placement signature and must not merge semantically different binding proposals.",
"Diversity pruning is optional and must be explicitly parameterized; no hidden diversity heuristic is allowed.",
"Diversity pruning may limit representation per explicit family such as spanColumnCount or placementMode, but it must not assign aesthetic quality.",
"Candidate lineage must preserve gridRef, columnGeometryRef, topologyRef, occupancyRegistryRef if used, requestRef, seed and source span/node refs.",
"Rejected candidate diagnostics are evidence; they are not scores.",
"8.03 emits no MetricResult score and no quality ranking; 8.04 owns grid variants/target scoring.",
"Candidate acceptance into a real layout is external to 8.03.",
"candidateSetRef must include a deterministic generation fingerprint so changed seed, budget, policy or allowed source set cannot collide with an older candidate set identity.",
"N/A != 0.",
"No beautyScore."
],
"hard_rules": [
"8.03 owns bounded deterministic ColumnGrid placement-candidate generation and candidate lineage only.",
"A ColumnPlacementCandidate describes horizontal X constraints against an already resolved Topic8 grid; it is not a complete 2D layout placement.",
"8.03 does not own Y placement, object height, typography, image crop, collision resolution, balance, hierarchy or eye flow.",
"Candidate generation consumes explicit Compo8.01 geometry and Compo8.02 topology; it does not reconstruct columns, spans, lines or nodes.",
"Every placement request is for one explicit contentRef. 8.03 must not form Cartesian products across candidate sets of multiple content items.",
"Every request requires an explicit deterministic seed and explicit GenerationBudget.",
"GenerationBudget.maxRawEvaluations is a hard upper bound on the request search-space cardinality. If potential candidate count exceeds it, return BUDGET_EXCEEDED; do not silently truncate search.",
"GenerationBudget.maxAcceptedCandidates is a hard upper bound on emitted candidates after filtering/deduplication.",
"If eligible candidates exceed maxAcceptedCandidates, selection is deterministic and seed-dependent using canonical candidate signatures; the same inputs and seed must reproduce the same subset.",
"A different seed may select a different subset but must not alter validity/hard-filter semantics.",
"Baseline placement modes are SPAN_INTERVAL, NODE_ANCHOR and SPAN_WITH_BOUNDARY_BINDINGS.",
"SPAN_INTERVAL uses an explicit contiguous ColumnSpan geometry from 8.01 and emits X_INTERVAL evidence only.",
"NODE_ANCHOR uses one explicit canonical GridNode and emits X_ANCHOR evidence only.",
"SPAN_WITH_BOUNDARY_BINDINGS uses a span interval and may propose left/right node bindings; these are proposed occupancy deltas, not mutations of the 8.02 registry.",
"Proposed bindings must reference the canonical boundary nodes of the selected span.",
"8.03 never mutates ColumnGridNodeOccupancyRegistry.",
"Occupancy filtering is allowed only through explicit CandidateOccupancyPolicy.",
"If occupancy evidence is required by policy and the registry is missing/N_A/PARTIAL for a queried node, the candidate cannot be silently treated as free.",
"COMPLETE registry FREE and PARTIAL registry UNKNOWN remain distinct during candidate filtering.",
"MULTI_OCCUPIED is not intrinsically invalid; it is filtered only if the explicit allowedNodeStates policy excludes it.",
"No universal preference for wider spans, centered spans, free nodes or particular anchor kinds exists.",
"Candidate de-duplication uses a canonical placement signature and must not merge semantically different binding proposals.",
"Diversity pruning is optional and must be explicitly parameterized; no hidden diversity heuristic is allowed.",
"Diversity pruning may limit representation per explicit family such as spanColumnCount or placementMode, but it must not assign aesthetic quality.",
"Candidate lineage must preserve gridRef, columnGeometryRef, topologyRef, occupancyRegistryRef if used, requestRef, seed and source span/node refs.",
"Rejected candidate diagnostics are evidence; they are not scores.",
"8.03 emits no MetricResult score and no quality ranking; 8.04 owns grid variants/target scoring.",
"Candidate acceptance into a real layout is external to 8.03.",
"candidateSetRef must include a deterministic generation fingerprint so changed seed, budget, policy or allowed source set cannot collide with an older candidate set identity.",
"N/A != 0.",
"No beautyScore."
],
"soft_constraints": [],
"preferences": [],
"overrides_allowed_by": [
"a newer explicit request/seed/budget may generate a different future candidate set",
"a newer topology/occupancy snapshot invalidates prior candidate sets that depend on it",
"historical candidate sets remain immutable and tied to original lineage"
],
"initial_heuristics": {
"seed_hash": {
"algorithm": "FNV-1a-like 32-bit deterministic string hash in reference runner",
"provenance": "IMPLEMENTATION_HEURISTIC",
"note": "sampling priority only; not quality"
}
},
"style_preset_values": [],
"candidate_generation": {
"bounded": true,
"seeded": true,
"deterministic": true,
"lineage_required": true,
"hard_filtering": true,
"deduplication": true,
"diversity_pruning": "explicit only",
"cross_content_cartesian_product": "FORBIDDEN"
},
"correction_policy": {
"foreign_content_mutation": "FORBIDDEN",
"budget_exceeded": "return BUDGET_EXCEEDED and require request decomposition/tighter source set or larger explicit budget",
"missing_geometry_span": "route to 8.01",
"missing_topology_node": "route to 8.02",
"missing_required_occupancy_evidence": "return N_A and request registry snapshot",
"registry_state_change": "invalidate candidate set; regenerate explicitly",
"placement_acceptance": "route to layout/integration owner",
"scoring_or_variant_choice": "route to 8.04",
"Y_placement_collision_typography": "route to their respective owners"
},
"deferred_inputs": [
"Compo8.04 variant/scoring contracts",
"future multi-object layout orchestrator combining independent candidate sets without hidden Cartesian explosion",
"Topic9 2D placement regions",
"Topic10 alignment evaluation",
"future collision/content-footprint owners"
],
"recompute_when": [
"request or seed changes",
"generation budget changes",
"allowed span/node source set changes",
"columnGeometryRef/topologyRef changes",
"occupancy registry snapshot changes when occupancyPolicy enabled",
"diversity policy changes"
],
"tests": [
"request validation",
"budget hard bound",
"span candidates",
"node anchor candidates",
"boundary binding proposals",
"occupancy filter complete/partial/N_A",
"multi occupied explicit handling",
"dedup signature",
"seed determinism",
"different seed subset",
"explicit diversity pruning",
"batch no cross-product",
"lineage",
"no registry mutation",
"no score/global leakage"
],
"finality": "BOUNDED_DETERMINISTIC_COLUMNGRID_X_PLACEMENT_CANDIDATE_GENERATOR_ONLY",
"candidate_set_identity": {
"candidateSetRef": "candidate-set:<requestRef>:<generationFingerprintHash>",
"generationFingerprint": "deterministic serialization of request generation inputs and lineage refs",
"includes": [
"requestRef",
"contentRef",
"gridRef",
"columnGeometryRef",
"topologyRef",
"occupancyRegistryRef",
"placementMode",
"allowedSpanRefs",
"allowedNodeRefs",
"boundaryBindingSides",
"bindingKind",
"occupancyPolicy",
"diversityPolicy",
"generationBudget",
"seed"
],
"important": "same requestRef with changed seed/budget/policy/source set produces a different candidateSetRef"
}
}