开启掘金成长之旅!这是我参与「掘金日新计划 · 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)