hoops_ai.ml.context_layer.ContextPredictor

class hoops_ai.ml.context_layer.ContextPredictor(context_provider, default_categorical_rule=None, default_numerical_rule=None, per_key_rules=None)

Bases: object

Predicts engineering context (metadata) for a query part from its nearest neighbors.

Given a list of VectorHit objects (from CADSearch.search_by_shape) and a set of metadata keys to infer, this class fetches per-hit metadata from a ContextProvider, extracts evidence per key, and dispatches each key to an AggregationRule.

Dispatch precedence:

  1. per_key_rules[key] if present.

  2. default_numerical_rule if key in context_provider.list_numeric_keys().

  3. default_categorical_rule otherwise.

Defaults are constructed lazily: CategoricalRule() and NumericWeightedRule() if you do not pass them.

Parameters:

Example

from hoops_ai.ml.context_layer import (

ContextPredictor, InMemoryContextProvider, CategoricalRule, NumericWeightedRule,

)

store = InMemoryContextProvider(

{“part-a”: {“Material”: “Steel”, “Cost”: 12.5}}, numeric_keys=[“Cost”],

) predictor = ContextPredictor(context_provider=store) predictions = predictor.infer(hits, keys=[“Material”, “Cost”]) # “Material” uses CategoricalRule (default), “Cost” uses NumericWeightedRule (default).

infer(hits, keys, query_context=None, *, return_evidence=False, status_policy=<object object>)

Infer context values from a list of search hits.

Metadata is fetched from the configured ContextProvider in a single batched call; VectorHit.metadata is not consulted.

Every key in keys is mapped to a ContextPrediction — the result is never None. When the underlying rule cannot produce a value (margin guard fired, no usable evidence, empty hit list) the returned ContextPrediction carries value=None and status=STATUS_INSUFFICIENT so callers can branch on a single, well-typed object.

status_policy controls how status is gated:

  • Not passedDEFAULT_STATUS_POLICY is applied. Lenient defaults give every non-abstaining prediction STATUS_READY; abstentions are STATUS_INSUFFICIENT.

  • Mapping → the caller’s policy is used (tighten any of min_observed_hits, min_observed_score_weight, min_top_share, min_margin).

  • Explicitly ``None`` → opt out of status evaluation entirely; predictions are still returned (never None) but their status is None and reasons is empty.

When keys mixes categorical and numeric entries, categoricals are inferred first and any prediction reaching STATUS_READY (ready_to_propose) is merged into the query_context passed to numeric rules. Numeric ContextPrediction objects carry the merged context on their injected_context field so callers can see what conditioned the numeric estimate. The output dict preserves the caller’s key order.

Parameters:
Return type:

dict[str, ContextPrediction]

property context_provider: ContextProvider
property default_categorical_rule: AggregationRule
property default_numerical_rule: AggregationRule
property per_key_rules: Mapping[str, AggregationRule]