Sigma Function(数论,思维)

题意描述

给定一个整数 N ,要求求出 x[1,N]σ(x) 为偶数的 x 的个数(σ(x) 表示 x 的正约数和)。
原题链接

分析


x 素因子分解之后得到

x=i=1kpiαi

σ(x) 的计算公式:

σ(x)=(p10+p11++p1α1)×(p20+p21++p2α2)××(pk0+pk1++pkαk)

我们不方便研究 σ(x) 为偶数的情况,我们可以研究 σ(x) 为奇数的情况,再用总数减掉奇数的个数即可。

我们要让 σ(x) 为奇数,则 σ(x) 的每一个因子都要为奇数,所以可以分开考虑公式的每一项:

  • 2x,则 (1+21+22++2α) 这一项一定为奇数,因为 2 的任何次幂都是偶数,加上 1 就变成了奇数。
  • 对于除了 2 以外的其他素因子,我们想要让 (1+p1+p2++pα) 为奇数,即想让 p1+p2++pα 为偶数,由于素因子的任何幂次都为奇数,所以只有当项数为偶数时,才能满足其为偶数,故可以得出其素因子的次数 αi 都为偶数

综上所述,满足 σ(x) 为奇数的数一定满足这样的形式:

x=2t×i=1kpiαi(piαi)

当次数都为偶数时,这个数其实就是一个完全平方数,所以可以简写成:

x=2t×mk

那么如何统计在 [1,N] 中这样的数的个数呢?

  • t 为偶数时,把 2 这个质因子囊括进来,x 就是一个完全平方数,这一部分就直接统计 [1,N] 当中的完全平方数就可以。
  • t 为奇数时,x2 就为完全平方数,所以再统计 [1,N] 中满足形式为 2×a×a 的形式的数即可。

Code:

// 原题链接:https://vjudge.net/problem/LightOJ-1336
#include <iostream>
#include <cstring>
#include <algorithm>

using namespace std;

typedef long long LL;

int main() {
    ios::sync_with_stdio(false); cin.tie(0);
    int T; cin >> T;
    for (int C = 1; C <= T; C ++ ) {
        LL n, res = 0; cin >> n;
        for (int i = 1; i <= n / i; i ++ ) {
            res ++ ;
            if ((LL)i * i * 2 <= n) res ++ ;
        }
        cout << "Case " << C << ": " << n - res << '\n';
    }
    return 0;
}
posted @   Xeus  阅读(261)  评论(0编辑  收藏  举报
编辑推荐:
· AI与.NET技术实操系列(二):开始使用ML.NET
· 记一次.NET内存居高不下排查解决与启示
· 探究高空视频全景AR技术的实现原理
· 理解Rust引用及其生命周期标识(上)
· 浏览器原生「磁吸」效果!Anchor Positioning 锚点定位神器解析
阅读排行:
· 全程不用写代码,我用AI程序员写了一个飞机大战
· DeepSeek 开源周回顾「GitHub 热点速览」
· 记一次.NET内存居高不下排查解决与启示
· MongoDB 8.0这个新功能碉堡了,比商业数据库还牛
· .NET10 - 预览版1新功能体验(一)
点击右上角即可分享
微信分享提示