题意:

定义函数\(f(n)\)为\(i \cdot j \not\equiv 0 \; (mod \; n)\)的数对\((i,j)\)的个数\((0 \leq i,j \leq n)\)

\(g(n)=\sum_{d|n}f(d)\),求\(g(n) \; mod \; 2^{64}\),其中\(1 \leq n \leq 10^9\)

仰慕叉老师手推公式

分析:

计算\(f(n)\)

\(f(n)\)不容易计算,但可以计算它的反面,也就是计算满足\(ij \equiv 0 \; (mod \; n)\)的数对\((i,j)\)的个数。

为了方便计算,对\(i,j\)的范围稍作改动,\(1 \leq i,j \leq n\),这不会影响最终计算结果。

\(i \cdot j\)是\(n\)的整数倍,也就是\(n\)被分到了这里面。

不妨设\(i=ax,j=by\),其中\(ab=n\)。我们可以枚举\(a\)来统计答案,但是这样有重复计算。

比如\((3 \cdot 2) \cdot (2 \cdot 1) = (6 \cdot 1) \cdot (2 \cdot 1) = 6 \cdot 2\),这样数对\((6, 2)\)在\(a=3\)和\(a=6\)时被计算了两次。

所以计数时我们规定,数对\((i,j)\)只会在\(a\)最大的时候被计算,所以有\(gcd(b,x)=1\)成立。

答案为\(\sum\limits_{a|n} \sum\limits_{1 \leq x \leq \frac{n}{a}}[gcd(x,b)=1] \cdot \frac{n}{b}=\sum\limits_{a|n}a \phi(\frac{n}{a})\)

计算\(g(n)\)

根据题中给的关系,得到\(g(n)=\sum\limits_{m|n}(m^2-f(m))=\sum\limits_{m|n}(m^2-\sum\limits_{d|m}d \phi(\frac{m}{d}))\)

继续化简后面那部分,\(\sum\limits_{m|n}\sum\limits_{d|m}d \phi(\frac{m}{d})\)交换求和顺序,得到\(\sum\limits_{d|n}d\sum\limits_{\frac{m}{d}|\frac{n}{d}}\phi(\frac{m}{d})\)

由于\(\sum\limits_{d|n} \phi(d)=n\),所以得到\(\sum\limits_{d|n}d \cdot \frac{n}{d}=n\sum\limits_{d|n}1=n \sigma(n)\)。其中\(\sigma(n)\)为\(n\)的约数的个数。

\(\sigma(n)\)可以这样计算:

首先将\(n\)质因数分解为\(\prod\limits_{i=1}^{r}p_{i}^{e_i}\),这样\(\sigma(n)=\prod\limits_{i=1}^{r}(e_i+1)\)。

因为我们已经将\(n\)分解,所以计算前面那部分的时候不要在\(\sqrt{n}\)内枚举\(n\)的约数,会超时的。要根据分解出来的结果直接枚举。

#include <iostream>
#include <cstdio>
#include <cstring>
#include <algorithm>
#include <cmath>
using namespace std; const int maxn = 32000 + 10;
int pcnt, prime[maxn];
bool vis[maxn]; void preprocess() {
for(int i = 2; i < maxn; i++) {
if(!vis[i]) prime[pcnt++] = i;
for(int j = 0; j < pcnt && i * prime[j] < maxn; j++) {
vis[i * prime[j]] = true;
if(i % prime[j] == 0) break;
}
}
} int tot, p[maxn], e[maxn]; unsigned long long ans;
void dfs(int d, unsigned long long product) {
if(d == tot) {
ans += product * product;
return ;
} dfs(d + 1, product);
for(int i = 1; i <= e[d]; i++) {
product *= p[d];
dfs(d + 1, product);
}
} int main()
{
preprocess();
int T; scanf("%d", &T);
while(T--) {
int n;
scanf("%d", &n); int t = n;
tot = 0;
for(int i = 0; i < pcnt && prime[i] * prime[i] <= n; i++) {
if(t % prime[i] == 0) {
p[tot] = prime[i];
e[tot] = 0;
while(t % prime[i] == 0) {
t /= prime[i];
e[tot]++;
}
tot++;
}
}
if(t > 1) { p[tot] = t; e[tot++] = 1; } unsigned long long tmp = 1;
for(int i = 0; i < tot; i++) tmp = tmp * (e[i] + 1);
tmp *= n; ans = 0;
dfs(0, 1); ans -= tmp; printf("%llu\n", ans);
} return 0;
}

HDU 5528 Count a * b 欧拉函数的更多相关文章

  1. HDU 4483 Lattice triangle(欧拉函数)

    题目链接:http://acm.hdu.edu.cn/showproblem.php?pid=4483 题意:给出一个(n+1)*(n+1)的格子.在这个格子中存在多少个三角形? 思路:反着想,所有情 ...

  2. hdu 2824 The Euler function(欧拉函数)

    题目链接:hdu 2824 The Euler function 题意: 让你求一段区间的欧拉函数值. 题解: 直接上板子. 推导过程: 定义:对于正整数n,φ(n)是小于或等于n的正整数中,与n互质 ...

  3. HDU - 2824 The Euler function 欧拉函数筛 模板

    HDU - 2824 题意: 求[a,b]间的欧拉函数和.这道题卡内存,只能开一个数组. 思路: ϕ(n) = n * (p-1)/p * ... 可利用线性筛法求出所有ϕ(n) . #include ...

  4. HDU 4002 Find the maximum(欧拉函数)

    题目链接 猜了一个结论,题面跟欧拉函数有关系. import java.util.*; import java.math.*; import java.text.*; import java.io.* ...

  5. HDU 1695 GCD (容斥原理+欧拉函数)

    题目链接 题意 : 从[a,b]中找一个x,[c,d]中找一个y,要求GCD(x,y)= k.求满足这样条件的(x,y)的对数.(3,5)和(5,3)视为一组样例 . 思路 :要求满足GCD(x,y) ...

  6. HDU 3501 Calculation 2 (欧拉函数)

    题目链接 题意 : 求小于n的数中与n不互质的所有数字之和. 思路 : 欧拉函数求的是小于等于n的数中与n互质的数个数,这个题的话,先把所有的数字之和求出来,再减掉欧拉函数中所有质数之和(即为eula ...

  7. HDU 3501 Calculation 2(欧拉函数)

    Calculation 2 Time Limit:1000MS     Memory Limit:32768KB     64bit IO Format:%I64d & %I64u Submi ...

  8. hdu 1695 GCD 容斥+欧拉函数

    题目链接 求 $ x\in[1, a] , y \in [1, b] $ 内 \(gcd(x, y) = k\)的(x, y)的对数. 问题等价于$ x\in[1, a/k] , y \in [1, ...

  9. hdu 2824 The Euler function 欧拉函数打表

    The Euler function Time Limit: 2000/1000 MS (Java/Others)    Memory Limit: 32768/32768 K (Java/Other ...

随机推荐

  1. c# 串口操作

    public class CommPort : IDisposable { public string Port = ""; ///<summary> ///波特率96 ...

  2. 关于使用mybatis的分页插件问题

    首先我需要导入架包 1.pagehelper 如果你是在mybatis中配置分页‘ 如下代码 <plugins> <plugin interceptor="com.gith ...

  3. npm使用快速的安装源(nrm)

    安装 npm install nrm --global 使用 nrm ls 切换安装源 nrm use taobao 测速 nrm test npm 参考地址:http://codingdict.co ...

  4. 用Python完成根据日期计算是星期几

    import datetime def week(year,month,day): someday=dayetime.date(year,month,day) result={ "0&quo ...

  5. java object默认的基本方法

    java object默认的基本方法中没有copy(),含有如下9个方法:  getClass(), hashCode(), equals(), clone(), toString(), notify ...

  6. sqlserver 查询某表的所有列名

    select name + ',' from syscolumns where id = object_id('SEND_TALLY') AND name <> 'PICDATAS'

  7. 如何处理错误消息Please install the Linux kernel header files

    Please install the Linux kernel "header" files matching the current kernel 当我启动minilkube时遇 ...

  8. Spark集群任务提交

    1. 集群管理器 Spark当前支持三种集群管理方式 Standalone—Spark自带的一种集群管理方式,易于构建集群. Apache Mesos—通用的集群管理,可以在其上运行Hadoop Ma ...

  9. Trie入门讲解

    我们常常用Trie(也叫前缀树)来保存字符串集合.如下图所示就是一个Trie. 上图表示的字符串集合为$\{a,to,tea,ted,ten,i,in,inn \}$,每个单词的结束位置对应一个“单词 ...

  10. 使用ErrorProvider组件验证文本框输入

    实现效果: 知识运用: ErrorProvider组件的BlinkStyle属性 //指示错误图标的闪烁时间 public ErrorBlinkStyle BlinkStyle{ get;set; } ...