Class EquivalenceClassModel

java.lang.Object
org.ek9lang.compiler.support.inputvariety.EquivalenceClassModel

public final class EquivalenceClassModel extends Object
Derives a type's TypeVariety — its value-class count + confidence — for the input-variation denominator (design §11.1). Pure, symbol/operator-driven, no literals.

Resolution order per type:

  1. Built-insBuiltinTypeClassModels (domain edges operators can't reveal), gated on the org.ek9. module prefix so a user type sharing a built-in's simple name is not mistaken for one.
  2. User enumerations (CLASS_ENUMERATION) — one class per member + unset, EXACT.
  3. User records with fields — a record is transparent, so a composite is a product of its fields: recurse on each field type and combine as a capped field-class cross-product (§4.4). This uses the structure we actually have instead of an opaque flat number. HEURISTIC in v1. Depth-bounded against self-referential / deeply-nested fields. (For composition, leavesOf(ISymbol) flattens a record to its field leaves rather than a single product — that is the primitive §4.5/§4.6 build on.)
  4. Everything else — classes, components, traits, opaque user types — the honest floor ClassConfidence.SET_UNSET_ONLY (count 2). A class encapsulates: its fields are private (§4.5), and — §12 decision (a) — a lone value's <=>/== buckets (below/at/above, equal/distinct) are relative to a reference point, not intrinsic and so not runtime-observable, so no operator heuristic is applied. Keeping the denominator at set/unset means the dynamic numerator can always reach 100% for such a type. Under-counting errs toward silence — the safe direction for a floor detector, never a false alarm.

Still deferred (each a §12 open decision): the collection cardinality × element model (built-in collections currently take the floor shape); an EXACT-composite gate-eligibility rule for records.

  • Field Details

    • RECORD_CLASS_CEILING

      static final int RECORD_CLASS_CEILING
      Record field-class cross-product ceiling (design §4.4 / §12.2). Large enough to preserve any realistic record's per-field product (e.g. Point{x,y} = 81), clamps only the pathological wide case, and keeps the downstream pairwise product overflow-safe. Records only — classes / components / traits do not decompose fields at all (§4.5 v3.2), they take the set/unset floor.
      See Also:
  • Constructor Details

    • EquivalenceClassModel

      public EquivalenceClassModel()
  • Method Details

    • varietyOf

      public TypeVariety varietyOf(ISymbol typeSymbol)
      The variety of a resolved type symbol; FLOOR for a null type (a parameter always has a resolved type by phase 5, so null is only a defensive guard).
    • leavesOf

      public List<TypeVariety> leavesOf(ISymbol typeSymbol)
      The scalar LEAF dimensions a type contributes to a callable's input space (design §4.5 v3.2 / §4.6) — the composition primitive. A RECORD is transparent, so it decomposes into its fields' leaves (recursively, depth- and width-bounded), each leaf carrying its own field-type confidence; a record therefore NEVER enters a pairwise product as an atomic count (that "product-of-products" was the t-escalation bug where Point.<=> reached 81×81=6561 instead of the honest per-leaf-pair 486). Everything else is a single scalar leaf — built-ins and enums by their own model, classes/components/traits as one opaque set/unset leaf (§12 decision (a), they encapsulate their state and expose no runtime-observable finer variety). Never empty (a leafless type yields the floor).
    • leafPathsOf

      public List<LeafPath> leafPathsOf(ISymbol typeSymbol)
      The same leaf dimensions leavesOf(ISymbol) counts, but as LeafPaths — each carrying the field steps walked to reach it. THE single flattening traversal: the denominator projects these to class counts, the numerator (§5) projects them to the field loads its probe emits, so the two can never disagree about a record's leaf order, nesting depth or width bound. Never empty (a leafless type yields the parameter itself as one opaque leaf, matching leavesOf(ISymbol)'s floor).
    • isEnumeration

      public boolean isEnumeration(ISymbol typeSymbol)
      True when this type's value-classes ARE its enumeration members — i.e. exactly the condition under which varietyOf(ISymbol) returns members + 1 at ClassConfidence.EXACT.

      The numerator asks this to decide whether a runtime value should be recorded by its member name rather than bucketed. It MUST agree with the denominator: were the numerator to emit member names for a type the denominator scored at the set/unset floor (2), the covered cells could exceed the floor and the construct would report over 100%. Hence one predicate, asked by both — not a genus check copied into the probe placer.

    • varietyOf

      TypeVariety varietyOf(String fullyQualifiedName, String simpleName)
      The name-keyed built-in-or-floor core — package-private so it is unit-testable without constructing symbols.