codexrichardson-derivative-error-orders.py
richardson-derivative-error-orders.py
"""Plot Richardson errors; run from _media with Python 3.14, NumPy, Matplotlib.
Outputs richardson-derivative-error-orders.png in the current directory.
Uses 70-digit Decimal Taylor sums to avoid a binary64 cancellation floor.
"""
from decimal import Decimal, localcontext
from pathlib import Path
import matplotlib
matplotlib.use("Agg")
import matplotlib.pyplot as plt
import numpy as np
def sinc(h):
term = total = Decimal(1)
for k in range(1, 60):
term *= -h * h / Decimal(2 * k * (2 * k + 1))
total += term
return total
def main():
h_values = np.geomspace(1e-3, 0.5, 130)
raw, extrapolated = [], []
with localcontext() as context:
context.prec = 70
for value in h_values:
h = Decimal(str(value))
a = sinc(h)
r = (4 * sinc(h / 2) - a) / 3
raw.append(float(abs(a - 1)))
extrapolated.append(float(abs(r - 1)))
assert min(raw) > 0 and min(extrapolated) > 0
plt.rcParams.update({"font.size": 11})
fig, ax = plt.subplots(figsize=(7.5, 5), layout="constrained")
ax.loglog(h_values, raw, color="#24679b", lw=2.4, label=r"Centered: $|A(h)-1|$")
ax.loglog(h_values, extrapolated, color="#c35724", lw=2.4,
label=r"Extrapolated: $|R(h)-1|$")
ax.loglog(h_values, h_values**2 / 6, "--", color="#163e5d", lw=1.2,
label=r"Second-order guide: $h^2/6$")
ax.loglog(h_values, h_values**4 / 480, "--", color="#71351b", lw=1.2,
label=r"Fourth-order guide: $h^4/480$")
ax.set(xlabel="Coarse step h (fine step h/2)", ylabel="Absolute error",
title=r"Sine derivative at zero: $A(h)=\sin(h)/h$, exact value 1")
ax.set_xlim(1e-3, 0.5)
ax.grid(which="major", color="#dce1e5", lw=0.8)
ax.legend(loc="upper left", fontsize=10, framealpha=1)
ax.text(0.97, 0.04, "70-digit arithmetic\nNo artificial error floor",
transform=ax.transAxes, ha="right", va="bottom", fontsize=9,
bbox={"facecolor": "white", "edgecolor": "#dce1e5", "pad": 5})
output = Path.cwd() / (Path(__file__).stem + ".png")
fig.savefig(output, dpi=120, facecolor="white", transparent=False)
plt.close(fig)
if __name__ == "__main__":
main()