@@ -0,0 +1,43 @@
|
||||
#!/usr/bin/env python3
|
||||
"""Generate integer Pow fixtures independently with Python's stdlib Decimal.
|
||||
|
||||
Use exact binary64 components, then Decimal integer exponentiation at 160 and
|
||||
240 significant decimal digits. Retain only rows whose floor after multiplication
|
||||
by 10**100 agrees at both precisions. Tests check both ends of the resulting
|
||||
100-decimal-place reference interval, far tighter than their DD error tolerance.
|
||||
No Python or generated data is needed when running the .NET tests.
|
||||
"""
|
||||
from decimal import Decimal, localcontext, ROUND_FLOOR
|
||||
import math
|
||||
|
||||
|
||||
def reference(high, low, exponent, precision):
|
||||
with localcontext() as context:
|
||||
context.prec = precision
|
||||
value = Decimal.from_float(high) + Decimal.from_float(low)
|
||||
result = context.power(value, exponent)
|
||||
return int((result * (Decimal(10) ** 100)).to_integral_value(rounding=ROUND_FLOOR))
|
||||
|
||||
|
||||
def main():
|
||||
inputs = [
|
||||
(1.0, math.ldexp(1.0, -54)),
|
||||
(1.0, -math.ldexp(1.0, -54)),
|
||||
(1.0 + math.ldexp(1.0, -30), math.ldexp(1.0, -84)),
|
||||
(1.0 - math.ldexp(1.0, -30), -math.ldexp(1.0, -84)),
|
||||
(1.00000003, math.ldexp(1.0, -55)),
|
||||
]
|
||||
for high, low in inputs:
|
||||
for exponent in [-2147483648, 2147483647]:
|
||||
first = reference(high, low, exponent, 160)
|
||||
second = reference(high, low, exponent, 240)
|
||||
assert first == second, (high, low, exponent)
|
||||
# Very tiny results need a relative rather than fixed-place interval;
|
||||
# these rows instead exercise the large positive-power fixture.
|
||||
if first == 0:
|
||||
continue
|
||||
print(f' [InlineData({high!r}, {low!r}, {exponent}, "{first}")]')
|
||||
|
||||
|
||||
if __name__ == "__main__":
|
||||
main()
|
||||
Reference in New Issue
Block a user