Class: Rigor::Inference::HktReducer
- Inherits:
-
Object
- Object
- Rigor::Inference::HktReducer
- Defined in:
- lib/rigor/inference/hkt_reducer.rb
Overview
ADR-20 Slice 2a โ reducer that walks a Definition's body_tree against a concrete
Type::App and returns a fully-typed Rigor::Type.
Reduction is the operational interpretation of ADR-20 ยง D4 ("Evaluation rules"):
- Resolve
F. Look up the registered body viaregistry.definition(uri). - Substitute arguments. Walk the body tree, replacing
{HktBody::Param}nodes with the matching positional arg from the application. - Build types.
{HktBody::TypeLeaf}returns its wrapped type as-is;{HktBody::Union}and{HktBody::NominalApp}route their reduced children throughType::Combinator.union/.nominal_ofso normalization applies. - Recurse on
{HktBody::AppRef}nodes. Reduce the args first; if the resulting(uri, args)matches an App already on the current reduction stack, return the in-progressType::Appcarrier as-is (lazy self-reference handling โ the standard "tying the knot" trick for recursive type aliases likejson::value). Otherwise build a freshType::Appand recursively reduce it against the same registry, sharing the fuel budget. - Fuel budget. Each visited node consumes one unit. On exhaustion, reduction unwinds to
app.bound.
The reducer is pure with respect to its inputs (the registry + the App) but uses a
per-call mutable state bag for fuel + cycle tracking. Concurrent reductions MUST allocate
fresh reducers (or fresh _reduce calls) โ the per-call state is not shared.
Defined Under Namespace
Classes: FuelExhausted, State
Constant Summary collapse
- DEFAULT_FUEL =
64
Instance Method Summary collapse
-
#initialize(registry) ⇒ HktReducer
constructor
A new instance of HktReducer.
-
#reduce(app, fuel: DEFAULT_FUEL) ⇒ Rigor::Type
Reduce
appagainst the registry.
Constructor Details
#initialize(registry) ⇒ HktReducer
Returns a new instance of HktReducer.
36 37 38 39 40 |
# File 'lib/rigor/inference/hkt_reducer.rb', line 36 def initialize(registry) raise ArgumentError, "registry must be an HktRegistry" unless registry.is_a?(HktRegistry) @registry = registry end |
Instance Method Details
#reduce(app, fuel: DEFAULT_FUEL) ⇒ Rigor::Type
Reduce app against the registry.
49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 |
# File 'lib/rigor/inference/hkt_reducer.rb', line 49 def reduce(app, fuel: DEFAULT_FUEL) raise ArgumentError, "expected a Rigor::Type::App, got #{app.class}" unless app.is_a?(Type::App) definition = @registry.definition(app.uri) return app.bound if definition.nil? || definition.body_tree.nil? return app.bound if definition.params.size != app.args.size state = State.new(fuel: fuel) begin state.with_in_progress(app.uri, app.args, app) do walk(definition.body_tree, bindings: bindings_for(definition, app.args), state: state) || app.bound end rescue FuelExhausted BudgetTrace.hit(BudgetTrace::HKT_FUEL_EXHAUSTED) app.bound end end |