repair_checks.py

back to table · edit · history · where entries came from · files · download

4736 bytes, as of the version from 2026-10-27 20:42 (current). Recorded here, not run.

"""T560 Programs repair checks. Run: sage -python repair_checks.py.
Download hyperelliptic_program.py, repair-document-before.json and repair-skill-evidence.json
alongside this file. The script prints JSON evidence and does not write to NumberDB.
The checked snippet uses double factorial products; the independent check uses
ordinary factorials, MPFI pi enclosures, and the CMSZ Proposition 6.13 recurrence.
"""
import json, sys, hashlib
from pathlib import Path
from decimal import Decimal
from math import factorial
import numberdb.sage as numberdb
from sage.env import SAGE_VERSION
from sage.rings.rational_field import QQ
from sage.rings.real_mpfi import RealIntervalField
from hyperelliptic_program import hyperelliptic_volume

base = Path(__file__).resolve().parent
I = RealIntervalField(768)

def coefficient(g, zeros):
    # Expand double factorials independently as ordinary factorials.
    if zeros == 1:
        return QQ(2*factorial(2*g-2)) / (2**(2*g-2)*factorial(g-1)**2*factorial(2*g+1))
    return QQ(2**(2*g+2)*factorial(g-1)*factorial(g)) / (factorial(2*g)*factorial(2*g+2))

assert coefficient(1,1) == coefficient(1,2) == QQ(1)/3
assert coefficient(2,1) == QQ(1)/120
assert coefficient(2,2) == QQ(1)/135
controls = ['marked torus coefficient 1/3', 'H(2) coefficient 1/120', 'labelled H(1,1) coefficient 1/135']
recurrence = []
for g in range(2,21):
    q1 = (2*g-1)*coefficient(g,1)
    rhs = q1 + sum(QQ(factorial(2*l-1)*factorial(2*(g-l)-1))*(2*l-1)*coefficient(l,1)*(2*(g-l)-1)*coefficient(g-l,1)/(4*factorial(2*g-1)) for l in range(1,g))
    assert rhs == g*g*coefficient(g,2)
    recurrence.append(g)

results=[]
for g in list(range(2,21))+[50,100]:
    for zeros in (1,2):
        value = hyperelliptic_volume(g, zeros, digits=100)
        other = I(coefficient(g,zeros))*I.pi()**(2*g)
        assert value.is_finite() and value > 0
        v = I(value)
        lo, hi = v.lower().exact_rational(), v.upper().exact_rational()
        rel_width = (hi-lo)/min(abs(lo), abs(hi))
        accuracy = rel_width.denominator().nbits() - rel_width.numerator().nbits() - 1
        assert accuracy >= numberdb.bits(100)
        assert v.lower().exact_rational() <= other.lower().exact_rational()
        assert v.upper().exact_rational() >= other.upper().exact_rational()
        results.append({'g':g,'zeros':zeros,'coefficient':str(coefficient(g,zeros)), 'relative_width_bits_lower_bound':int(accuracy), 'mpfi_contained':True})

def exact_decimal(text):
    d = Decimal(text)
    sign, digits, exponent = d.as_tuple()
    numerator = int(''.join(map(str,digits)))*(-1 if sign else 1)
    scale = QQ(10)**exponent
    return QQ(numerator)*scale, scale

doc=json.loads((base/'repair-document-before.json').read_text())
stored=[]
for gs, profiles in doc['Numbers'].items():
    g=int(gs)
    for profile, components in profiles.items():
        if 'hyp' not in components:
            continue
        zeros=len(profile.split(','))
        mid,ulp = exact_decimal(components['hyp']['number'])
        v=I(hyperelliptic_volume(g,zeros))
        lo,hi=v.lower().exact_rational(),v.upper().exact_rational()
        assert mid-ulp <= lo <= hi <= mid+ulp
        stored.append({'g':g,'profile':profile,'ulp_endpoint_error':str(I(max(abs(lo-mid),abs(hi-mid))/ulp)), 'contained':True})
assert len(stored)==6
for g, zeros in [(1,1),(0,2),(2,0),(2,3),(QQ(5)/2,1)]:
    try:
        hyperelliptic_volume(g,zeros)
    except (ValueError, TypeError):
        pass
    else:
        raise AssertionError('invalid input accepted')
result={
    'table':'T560', 'sage_version':SAGE_VERSION, 'skill_evidence':json.loads((base/'repair-skill-evidence.json').read_text()),
    'snippet_sha256':hashlib.sha256((base/'hyperelliptic_program.py').read_bytes()).hexdigest(),
    'document_before_sha256':hashlib.sha256((base/'repair-document-before.json').read_bytes()).hexdigest(),
    'sources':[{'url':'https://arxiv.org/pdf/1901.01785','locator':'Section 6.5, formulas following Proposition 6.13; Proposition 6.13 recurrence'}, {'url':'https://arxiv.org/pdf/1212.1660','locator':'Remark 1.2, labelled genus-two coefficients'}],
    'controls':controls, 'recurrence_genera':recurrence, 'evaluations':results, 'stored_hyperelliptic_intervals':stored,
    'minimum_relative_width_bits_lower_bound':min(r['relative_width_bits_lower_bound'] for r in results),
    'argument_uncertainty':'Genus and number of zeros are exact integers; rational coefficients are exact. Both Arb and MPFI propagate the enclosure of pi through the power and rational multiplication.',
    'scope':'Programs repair only; no stored values changed. Checks do not independently rederive the 19 nonhyperelliptic entries.',
    'ok':True
}
print(json.dumps(result,indent=2))