notes.html

problem 9 · 21 lines

<article>
<h3>Problem Analysis</h3>
<p>
A <a class="reference-source" href="https://en.wikipedia.org/wiki/Pythagorean_triple" rel="noopener noreferrer" target="_blank">Pythagorean triple</a> is a set of three positive integers a &lt; b &lt; c satisfying a<sup>2</sup> + b<sup>2</sup> = c<sup>2</sup>. Finding such integers is a <a class="reference-source" href="https://en.wikipedia.org/wiki/Diophantine_equation" rel="noopener noreferrer" target="_blank">Diophantine equation</a> - an equation for which we admit only integer solutions. Here I add a second constraint, the linear equation a + b + c = S, and must find the unique <a class="reference-source" href="https://en.wikipedia.org/wiki/Pythagorean_triple" rel="noopener noreferrer" target="_blank">Pythagorean triple</a> satisfying both, then report the product abc.
</p>
<p>
The crucial observation is that the linear constraint lets me eliminate one variable. Once a and b are chosen, c is completely determined: c = S - a - b. This collapses what would naively be a three-dimensional search into a two-dimensional one. Two further observations bound the loops tightly. First, because a &lt; b &lt; c are all positive and sum to S, the smallest value a cannot exceed roughly S/4 - if a were any larger we could not fit two strictly greater values b and c that still sum to S. Second, b is bounded above by S/2 to keep c positive. Each candidate (a, b) pair is checked in constant time, so the overall complexity is <a class="reference-source" href="https://en.wikipedia.org/wiki/Big_O_notation" rel="noopener noreferrer" target="_blank">O(S<sup>2</sup>)</a>. For S = 1000 that is on the order of 10<sup>5</sup> iterations - trivially fast in any language.
</p>
<h3>Solution Approach</h3>
<h4>Bounded two-variable search (index 0, Python and C)</h4>
<p>
Both the Python and C solutions implement the same algorithm. The outer loop iterates a from 1 up to S/4 inclusive - the tightest upper bound derivable from the ordering a &lt; b &lt; c. The inner loop iterates b from a (which enforces a ≤ b) up to S/2 (which keeps c positive). For each pair, c is computed directly as S - a - b rather than searched for. This is the variable-elimination step that removes an entire loop level. I then test whether a<sup>2</sup> + b<sup>2</sup> == c<sup>2</sup> and, because the problem guarantees exactly one solution, return a*b*c immediately on the first match. The two nested loops give the <a class="reference-source" href="https://en.wikipedia.org/wiki/Big_O_notation" rel="noopener noreferrer" target="_blank">O(S<sup>2</sup>)</a> bound established above.
</p>
<p>
I deliberately compute c as an integer expression rather than taking a floating-point square root of a<sup>2</sup> + b<sup>2</sup>. Integer arithmetic is exact, so the equality check is reliable; a floating-point approach would demand a tolerance comparison and risk rounding errors. The closed-form c = S - a - b sidesteps all of that.
</p>
<p>
The Python version wraps the nested loops in a <a class="reference-source" href="https://docs.python.org/3/reference/expressions.html#generator-expressions" rel="noopener noreferrer" target="_blank">generator expression</a> and calls <code>next()</code> to retrieve the first result, converting the resulting <code>StopIteration</code> into a descriptive <code>ValueError</code> when no triple exists. The C version uses plain nested <code>for</code> loops with an early <code>return</code>, writing a diagnostic to <code>stderr</code> and returning -1 on failure. In C I cast to <code>long long</code> before the multiplication: although the answer 31875000 fits comfortably in a 32-bit <code>int</code>, the product of three loop variables could overflow for larger inputs, and promoting first is a cheap, defensive habit. Both versions handle the dev case (S = 12, the classic 3-4-5 triple, product 60) and the main case correctly.
</p>
</article>