兩版代碼唯一差別:if (i == s) k++; 的位置——版本一在內層循環內,版本二在外層循環內。版本一無輸出,版本二正常。
變量 s 在內層循環中逐漸累加。版本一每次累加後立即判斷 i == s,若中間某步恰好相等(但最終 s > i),k 會被錯誤遞增,導致計數失真。
// 版本一:錯誤
for (i = 2; i <= 20000; i++, s = 0) {
for (j = 1; j < i; j++) {
if (i % j == 0) s += j;
if (i == s) k++; // 過早判斷!s 還在累加中
}
if (k == n) { ... }
}
// 版本二:正確
for (i = 2; i <= 20000; i++, s = 0) {
for (j = 1; j < i; j++) {
if (i % j == 0) s += j;
}
if (i == s) k++; // 內層循環結束,s 確定,再判斷
if (k == n) { ... }
}
i/2 或 sqrt(i),成對累加因子。累加類變量的最終判斷,必須放在累加循環結束之後。這是「邏輯時機」錯誤的典型案例:變量未穩定時過早使用,導致中間態污染結果。調試時多打印關鍵變量變化,一眼可見。