Repository navigation
Root the reciprocal in integers for a negative-degree RootN [patch] - #161
Merged
Merged
Conversation
RootN(x, -n, d) took the root at d+2 digits, its reciprocal at d+2, and rounded again to d, so a value near a rounding boundary came out one unit wrong in the last place (RootN(3, -3, 10) gave 0.6933612743). It now takes the integer root of floor(10^k / s) directly: the floor of the root of a floor is the floor of the root, so the digits are the true value truncated and the single rounding to d is correct. Fixes #142 Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01VL7qukbkUpkVRArT45bBFb
|
This was referenced Oct 7, 2026
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.



Fixes #142
Before:
RootN(x, -n, d)wasDivideApproximation(One, RootN(x, n, d + 2), d + 2, d). That rounds three times, and two guard digits can't absorb two of those roundings near a boundary. SoRootN(3, -3, 10)returned 0.6933612743, where the correct answer is …744. The issue's sweep found 27 of 3,588 cases wrong, including some at 50 digits.After: the negative path takes the root of the reciprocal directly in integers, as the issue's preferred fix describes:
PositiveReciprocalRootNcomputesq = floor(10^k / s).kis chosen so thatqhas at leastn·(d+2)digits andndivides the exponent-k - e.IntegerRootN(q, n). Sincefloor(floor(y)^(1/n)) = floor(y^(1/n)), the root is the true value truncated, and oneReduceSignificance(d)rounds it correctly.10^k % s == 0androot^n == q. That matches how the positive path treats exact roots.xkeeps the old behaviour: an even degree throwsArgumentOutOfRangeException, and an odd degree carries the sign. Zero still throwsDivideByZeroException. A degree of -1 usesqdirectly, without a root.Tests:
TestNegativeDegreeRootRoundsOnceFromTheTrueValuepins the issue's table:RootN(3, -3, 10) == 0.6933612744,RootN(20, -2, 10) == 0.2236067977, plus (47, -2, 5), (41, -3, 5), (0.5, -3, 8), (1.5, -3, 6), and a negative odd case.TestNegativeDegreeRootsAgreeWithAWideReciprocalAcrossASweepcovers the issue's differential sweep: k = 2..300, n ∈ {-2, -3, -5}, d ∈ {5, 10, 20, 50}. It compares each result with1 / RootN(k, n, d+40)rounded tod. That reference goes through the positive path andDivide, so it shares no code with the path under test.main, both tests fail (RootN(3, -3, 10)andRootN(47, -2, 5)are wrong). With this change both pass. Full suite: 442 passed, 0 failed.This doesn't touch #127 (
FractionalPowdouble rounding). That one goes throughexp(y·ln x), so the integer-root approach doesn't carry over directly.🤖 Generated with Claude Code
https://claude.ai/code/session_01VL7qukbkUpkVRArT45bBFb
Generated by Claude Code