fhelium.experimental.bootstrap.polynomial.power
Encrypted evaluators for power-basis polynomials.
BalancedPowerEvaluator
class View source
BalancedPowerEvaluator(skip_near_zero: float = 0.0)Evaluate a power series through a shared balanced product tree.
To construct
evaluate consumes a two-component coefficient-domain, standard-RNS Q ciphertext representing the basis coordinate [component, *batch, limb, coefficient]; all batch members share depth, scale, and prime_ids. The method is functional. Each ciphertext product converts operands to NTT/Montgomery form, multiplies to three components, relinearizes back to two coefficient-domain standard components, and rescales by the complete Q group product while retaining actual scale. The final result is coefficient-domain standard RNS over Q at ciphertext.depth + required_depths(polynomial), with the corresponding prime_ids, unchanged batch shape, two components, and the coefficient-product target scale.
Attributes
| Name | Type | Default/value |
|---|---|---|
skip_near_zero | float | 0.0 |
operation_inventory
method
def operation_inventory(polynomial: PolynomialApproximation) -> dict[str, int]: ...Return multiplying operations executed by evaluate.
Coefficient multiplication counts only active nonconstant terms. Alignment multiplication counts every multiply-by-one depth advance, including advances used inside the shared power tree and before term addition. Additions and plaintext encoding are not multiplications.
required_depths
method
def required_depths(polynomial: PolynomialApproximation) -> int: ...Count the deepest balanced-product path and coefficient product.
evaluate
method
def evaluate(arithmetic: BootstrapArithmetic, ciphertext: Ciphertext, polynomial: PolynomialApproximation, *, relinearization_key: RelinearizationKey | None=None) -> Ciphertext: ...Evaluate
Coefficients with magnitude at or below skip_near_zero are omitted. A constant-only polynomial still consumes one depth by multiplying the input by zero; this keeps the execution behavior equal to the declared one-depth cost. Inputs are not mutated and output storage does not alias an input.
HornerPowerEvaluator
class View source
HornerPowerEvaluator()Evaluate a power polynomial by a corrected depth-aware Horner chain.
For degree
and then applies
A constant polynomial deliberately consumes one depth by multiplying the input by zero. A linear polynomial consumes one coefficient-multiplication depth and requires no relinearization key. Degree
required_depths
method
def required_depths(polynomial: PolynomialApproximation) -> int: ...Return one depth for constants or the declared power degree.
operation_inventory
method
def operation_inventory(polynomial: PolynomialApproximation) -> dict[str, int]: ...Return the corrected-Horner multiplication inventory.
evaluate
method
def evaluate(arithmetic: BootstrapArithmetic, ciphertext: Ciphertext, polynomial: PolynomialApproximation, *, relinearization_key: RelinearizationKey | None=None) -> Ciphertext: ...Evaluate a power polynomial with a corrected Horner recurrence.
The input must be a complete two-component coefficient-domain, standard-RNS Q ciphertext at its recorded actual scale. The method validates all context, key, scale, and available-depth requirements before allocating encrypted temporaries. The functional output is in the same arithmetic state at ciphertext.depth + required_depths(polynomial) and the arithmetic owner's target scale.
PatersonStockmeyerPowerEvaluator
class View source
PatersonStockmeyerPowerEvaluator(baby_step: int)Evaluate a power polynomial with one fixed baby-step size.
baby_step=k is part of the evaluator identity and is never selected at runtime. The evaluator writes
Balanced shared powers
Basis powers follow the input's actual scale recurrence. Coefficient accumulators use a common multiple of those scales chosen so the final product reaches the requested output scale. This keeps additions coherent without changing the polynomial's coefficients or its input coordinate.
The declared coefficient tuple, including zero entries, fixes the schedule. baby_step therefore controls a reproducible DAG rather than an unreliable degree-only estimate.
Attributes
| Name | Type | Default/value |
|---|---|---|
baby_step | int |
required_depths
method
def required_depths(polynomial: PolynomialApproximation) -> int: ...Return the critical-path depth cost for this fixed k.
operation_inventory
method
def operation_inventory(polynomial: PolynomialApproximation) -> dict[str, int]: ...Return ciphertext, coefficient, and alignment counts.
evaluate
method
def evaluate(arithmetic: BootstrapArithmetic, ciphertext: Ciphertext, polynomial: PolynomialApproximation, *, relinearization_key: RelinearizationKey | None=None) -> Ciphertext: ...Evaluate with the fixed baby/giant schedule and depth caches.