507. 完美数

121 阅读1分钟

开启掘金成长之旅!这是我参与「掘金日新计划 · 12 月更文挑战」的第24天,点击查看活动详情

一、题目描述:

507. 完美数 - 力扣(LeetCode) (leetcode-cn.com)

对于一个 正整数,如果它和除了它自身以外的所有 正因子 之和相等,我们称它为 「完美数」。

给定一个 整数 n, 如果是完美数,返回 true;否则返回 false。

示例 1:

输入:num = 28
输出:true
解释:28 = 1 + 2 + 4 + 7 + 14
1, 2, 4, 7, 和 14 是 28 的所有正因子。

示例 2:

输入:num = 7
输出:false

提示:

  • 1 <= num <= 10^8

二、思路分析:

由于因素必然成对出现,以num的平方根:mid为对称的中心,只需要遍历mid前的所有因数,就可以得到其对应的因数
这样就可以以较小代价遍历所有因数
同时对于num是完全平方根的情况下,只需要在for的条件失效,即dd>=num时
判断是否有dd=num,如果满足情况,就把d加进去,这样可以节约很多次的判断,进一步优化时间空间开销

三、AC 代码:

bool checkPerfectNumber(int num){
    //遍历得到他的所有正因子之和,直接累加
    if (num <= 5) {
        return false;
    }

    int sum = 1;
    //1必然是一个因素,可以提前统计,同时防止遍历到它对应的另一个因数num上
    int d;
    for (d = 2; d * d < num; ++d) {
        //因素必然成对出现,且对称的中值就是num的平方根
        //现在值统计num的平方以前的因数和这个因数对应的因数
        if (num % d == 0) {
            sum += (d + num / d);
        }
    }

    if (d * d == num) {
        sum +=  d;
    }
    //假如num是完全平方数,他的平方根也只能算一次

    return sum == num;

}

范文参考

Rust/Golang/Java 打表/暴力枚举优化 100%击败 - 完美数 - 力扣(LeetCode)

【微扰理论】枚举|提前祝大家元旦快乐! - 完美数 - 力扣(LeetCode)

【完美数】【C语言详解】【3种思路】 - 完美数 - 力扣(LeetCode)