You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Python真约数求和程序结果错误排查及优化咨询

错误根源分析

你的代码核心问题是循环变量k的自增逻辑重复,导致命中约数判断时会跳过下一个整数:

  • 当n % k == 0条件成立时,你在if代码块内写了k += 1
  • 紧接着if块结束后,又无条件执行了一行k = k + 1

这就导致只要当前k是n的约数,单次循环k就会总共加2,直接跳过k+1这个数的判断,自然会漏掉2、4这类连续的约数:

  • 计算36的约数时,k=1命中判断,if内k变成2,出if又加1变成3,直接跳过了k=2的校验;k=3命中判断时,if内k变成4,出if又加1变成5,跳过k=4的校验,总共少加了2+4=6,55-6=49,和你实际输出完全一致
  • 计算102的约数时,k=1命中判断后直接跳到k=3,少加了2,114-2=112,和你实际输出一致
  • 测试用例n=3返回1属于巧合:跳过的k=2本来就不是3的约数,没有影响最终结果

另外你代码里对k反复调用int()是多余操作,k从初始化开始就是整数类型,不需要重复转换。

基础修复版本

只需要把k的自增逻辑统一放到循环末尾,每次循环只自增1次,不要在if块内重复写自增逻辑即可,同时补上n≤1的边界判断:

def sum_divisors(n):
    # 小于等于1的数没有真约数,直接返回0
    if n <= 1:
        return 0
    k = 1
    total = 0
    while k < n:
        if n % k == 0:
            total += k
        k += 1  # 所有分支统一自增1,避免跳数
    return total

# 测试用例
print(sum_divisors(0))   # 0
print(sum_divisors(3))   # 1
print(sum_divisors(36))  # 55
print(sum_divisors(102)) # 114

运行后所有测试用例返回结果完全符合预期。

性能优化版本

上面的基础版时间复杂度是O(n),当n取值很大时运行效率很低。利用「约数成对出现」的特性,只需要遍历到√n就可以找到所有约数,时间复杂度可以降到O(√n),大数值场景下性能提升非常明显:

import math

def sum_divisors(n):
    if n <= 1:
        return 0
    total = 1  # 1是所有大于1的整数的真约数,直接初始化
    sqrt_n = int(math.sqrt(n))
    # 从2遍历到平方根即可,成对收集约数
    for k in range(2, sqrt_n + 1):
        if n % k == 0:
            total += k
            pair = n // k
            # 避免重复加完全平方数的平方根,同时排除等于n本身的约数
            if pair != k and pair != n:
                total += pair
    return total

优化点说明:

  • 不需要从1遍历到n-1,遍历上限到n的平方根即可,比如计算1000000的真约数和,只需要循环1000次,远低于基础版的100万次
  • 提前处理边界值,避免n=0、n=1时出现无意义的循环
  • 去掉了冗余的类型转换,代码更简洁

内容的提问来源于stack exchange,提问作者Warrior

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.27 18:31:28