题意:

求\(\sum_{i=1}^n\varphi(i)\)和\(\sum_{i=1}^n\mu(i)\)

思路:

由性质可知:\(\mu*I=\epsilon,\varphi*I=id\)那么可得:

\[S_{\varphi}(n)=\sum_{i=1}^n\varphi(i)=\frac{(n+1)n}{2}-\sum_{i=2}^nS_{\varphi}(\lfloor\frac{n}{i}\rfloor)\\
S_{\mu}(n)\sum_{i=1}^n\mu(i)=1-\sum_{i=2}^nS_{\mu}(\lfloor\frac{n}{i}\rfloor)
\]

然后用现预处理一部分答案,然后数论分块其他答案,用记忆化记录中间答案。

很卡常...

还有一种不用\(map\)的方法,详见代码\(2\)。

代码:

#include<map>
#include<set>
#include<cmath>
#include<cstdio>
#include<stack>
#include<ctime>
#include<vector>
#include<queue>
#include<cstring>
#include<string>
#include<sstream>
#include<iostream>
#include<algorithm>
#include<unordered_map>
typedef long long ll;
typedef unsigned long long ull;
using namespace std;
const int maxn = 6000000 + 5;
const ll MOD = 998244353;
const ull seed = 131;
const int INF = 0x3f3f3f3f; int vis[maxn];
int prime[maxn], cnt;
int N = 6000000;
ll mu[maxn], phi[maxn];
unordered_map<int, int> mmu;
unordered_map<int, ll> mphi;
void init(int n){
cnt = 0;
mu[1] = 1;
phi[1] = 1;
for(int i = 2; i <= n; i++){
if(!vis[i]){
prime[cnt++] = i;
mu[i] = -1;
phi[i] = i - 1;
}
for(int j = 0; j < cnt && prime[j] * i <= n; j++){
vis[i * prime[j]] = 1;
if(i % prime[j] == 0){
mu[i * prime[j]] = 0;
phi[i * prime[j]] = phi[i] * prime[j];
break;
}
mu[i * prime[j]] = -mu[i];
phi[i * prime[j]] = phi[i] * (prime[j] - 1);
}
} for(int i = 2; i <= n; i++){
phi[i] += phi[i - 1];
mu[i] += mu[i - 1];
}
} ll Sphi(int n){
if(n <= N) return phi[n];
if(mphi.count(n)) return mphi[n];
ll ans = 1LL * n * (1 + n) >> 1LL;
for(int l = 2, r; l <= n; l = r + 1){
r = min(n / (n / l), n);
ans -= (r - l + 1) * Sphi(n / l);
}
return mphi[n] = ans;
}
int Smu(int n){
if(n <= N) return mu[n];
if(mmu.count(n)) return mmu[n];
int ans = 1;
for(int l = 2, r; l <= n; l = r + 1){
r = min(n / (n / l), n);
ans -= (r - l + 1) * Smu(n / l);
}
return mmu[n] = ans;
} int main(){
init(N);
int T;
scanf("%d", &T);
while(T--){
int n;
scanf("%d", &n);
printf("%lld %d\n", Sphi(n), Smu(n));
}
return 0;
}
#include<map>
#include<set>
#include<cmath>
#include<cstdio>
#include<stack>
#include<ctime>
#include<vector>
#include<queue>
#include<cstring>
#include<string>
#include<sstream>
#include<iostream>
#include<algorithm>
typedef long long ll;
typedef unsigned long long ull;
using namespace std;
const int maxn = 6000000 + 5;
const ll MOD = 998244353;
const ull seed = 131;
const int INF = 0x3f3f3f3f;
int vis[maxn];
int prime[maxn], cnt;
int N = 6000000;
ll phi[maxn], mphi[100000];
int mu[maxn], mmu[100000];
int vis2[100000];
int n, up;
void init(int n){
cnt = 0;
mu[1] = 1;
phi[1] = 1;
for(int i = 2; i <= n; i++){
if(!vis[i]){
prime[cnt++] = i;
mu[i] = -1;
phi[i] = i - 1;
}
for(int j = 0; j < cnt && prime[j] * i <= n; j++){
vis[i * prime[j]] = 1;
if(i % prime[j] == 0){
mu[i * prime[j]] = 0;
phi[i * prime[j]] = phi[i] * prime[j];
break;
}
mu[i * prime[j]] = -mu[i];
phi[i * prime[j]] = phi[i] * (prime[j] - 1);
}
} for(int i = 2; i <= n; i++){
phi[i] += phi[i - 1];
mu[i] += mu[i - 1];
}
}
int getmu(int x){
return x <= N? mu[x] : mmu[up / x];
}
ll getphi(int x){
return x <= N? phi[x] : mphi[up / x];
}
void solve(int n){
int t = up / n;
if(n <= N) return;
if(vis2[t]) return;
vis2[t] = 1;
mmu[t] = 1, mphi[t] = 1LL * n * (n + 1) / 2;
for(int l = 2, r; l <= n; l = r + 1){
r = n / (n / l);
solve(n / l);
mmu[t] -= (r - l + 1) * getmu(n / l);
mphi[t] -= (r - l + 1) * getphi(n / l);
}
} int main(){
init(N);
int T;
scanf("%d", &T);
while(T--){
scanf("%d", &n);
up = n;
if(n <= N) printf("%lld %d\n", phi[n], mu[n]);
else{
memset(vis2, 0, sizeof(vis2));
solve(n);
printf("%lld %d\n", mphi[1], mmu[1]);
}
}
return 0;
}

P4213 【模板】杜教筛(杜教筛)题解的更多相关文章

  1. 【51NOD 1847】奇怪的数学题(莫比乌斯反演,杜教筛,min_25筛,第二类斯特林数)

    [51NOD 1847]奇怪的数学题(莫比乌斯反演,杜教筛,min_25筛,第二类斯特林数) 题面 51NOD \[\sum_{i=1}^n\sum_{j=1}^nsgcd(i,j)^k\] 其中\( ...

  2. 【LOJ#572】Misaka Network 与求和(莫比乌斯反演,杜教筛,min_25筛)

    [LOJ#572]Misaka Network 与求和(莫比乌斯反演,杜教筛,min_25筛) 题面 LOJ \[ans=\sum_{i=1}^n\sum_{j=1}^n f(gcd(i,j))^k\ ...

  3. hdu6607 min25筛+杜教筛+伯努利数求k次方前缀和

    推导过程类似https://www.cnblogs.com/acjiumeng/p/9742073.html 前面部分min25筛,后面部分杜教筛,预处理min25筛需要伯努利数 //#pragma ...

  4. 素数筛&&欧拉筛

    折腾了一晚上很水的数论,整个人都萌萌哒 主要看了欧拉筛和素数筛的O(n)的算法 这个比那个一长串英文名的算法的优势在于没有多次计算一个数,也就是说一个数只筛了一次,主要是在%==0之后跳出实现的,具体 ...

  5. 欧拉筛,线性筛,洛谷P2158仪仗队

    题目 首先我们先把题目分析一下. emmmm,这应该是一个找规律,应该可以打表,然后我们再分析一下图片,发现如果这个点可以被看到,那它的横坐标和纵坐标应该互质,而互质的条件就是它的横坐标和纵坐标的最大 ...

  6. 【51nod1847】奇怪的数学题(Min_25筛+杜教筛)

    题面 传送门 题解 这题有毒--不知为啥的错误调了半天-- 令\(f(i)={sgcd(i)}\),那么容易看出\(f(i)\)就是\(i\)的次大质因子,用\(i\)除以它的最小质因子即可计算 于是 ...

  7. LOJ572. 「LibreOJ Round #11」Misaka Network 与求和 [莫比乌斯反演,杜教筛,min_25筛]

    传送门 思路 (以下令\(F(n)=f(n)^k\)) 首先肯定要莫比乌斯反演,那么可以推出: \[ ans=\sum_{T=1}^n \lfloor\frac n T\rfloor^2\sum_{d ...

  8. HDU 6706 huntian oy(杜教筛 + 一些定理)题解

    题意: 已知\(f(n,a,b)=\sum_{i=1}^n\sum_{j=1}^igcd(i^a-j^a,i^b-j^b)[gcd(i,j)=1]\mod 1e9+7\),\(n\leq1e9\),且 ...

  9. 欧拉筛(线性筛) & 洛谷 P3383 【模板】线性筛素数

    嗯.... 埃氏筛和欧拉筛的思想都是相似的: 如果一个数是素数,那么它的所有倍数都不是素数.... 这里主要介绍一下欧拉筛的思路:(欧拉筛的复杂度大约在O(n)左右... 定义一个prime数组,这个 ...

  10. 洛谷 P3383 【模板】线性筛素数-线性筛素数(欧拉筛素数)O(n)基础题贴个板子备忘

    P3383 [模板]线性筛素数 题目描述 如题,给定一个范围N,你需要处理M个某数字是否为质数的询问(每个数字均在范围1-N内) 输入输出格式 输入格式: 第一行包含两个正整数N.M,分别表示查询的范 ...

随机推荐

  1. 三十二:WEB漏洞-文件操作之文件下载读取全解

    文件下载读取 原路,检测,利用,修复 利用 数据库配置文件下载或者读取后续 接口密钥信息文件下载或者读取后续 文件名,参数值,目录符号 read.xxx?filename= down.xxx?file ...

  2. python中json模块的使用

    Python自带json模块,它有loads.dumps.load和dump这4个功能,用于Json格式字符串和Python数据类型间进行转换. 一.json.loads() 把Json格式字符串解码 ...

  3. CoeMonkey少儿编程第4章 变量

    点击这里,现在就开启CodeMonkey的趣味编程之旅. 目标 了解什么是变量 了解变量的命名规则 掌握如何使用变量 变量 什么是变量?顾名思义,变量就是可以变化的量. 和变量相对的是常量,即不可变化 ...

  4. CUDA 介绍

    1. 介绍 1.1 GPU vs. CPU GPU 使用更多的晶体管进行数据处理,而不是数据缓存和流控制,因此可以提供高度的并行计算. GPU 可以通过计算来隐藏内存访问延迟,而不是依赖于大量的数据缓 ...

  5. windows10复制粘贴键突然失效无法复制粘贴的最简单办法

    报了学习班,打开了VCE的加密文档 今天复制粘贴键突然失效 在网上捣鼓了好多方法都不行最后发现看看你有没有在用加密文件,也就是网课类的文档和视频.有就把它关了关了就好了

  6. What is :: (double colon) in Python when subscripting sequences?

    What is :: (double colon) in Python when subscripting sequences? 15 Extended Slices https://docs.pyt ...

  7. super 多重继承 super() function with multilevel inheritance

    Python | super() function with multilevel inheritance - GeeksforGeeks https://www.geeksforgeeks.org/ ...

  8. tcpdump 参数详解及使用案例

    参数 -A 以ASCII码方式显示每一个数据包(不会显示数据包中链路层头部信息). 在抓取包含网页数据的数据包时, 可方便查看数据(nt: 即Handy for capturing web pages ...

  9. linux日志中查找关键字、前几行、结尾几行,Linux的find用法示例

    linux在日志中查找关键字.前几行.结尾几行,Linux的find用法示例 1.linux在日志中查找关键字.前几行.结尾几行 1.1查看日志 前 n行: 1.2查看日志 尾 n行: 1.3根据 关 ...

  10. php之PDO连接mysql数据库,增删改查等等操作实例

    我们使用传统的 mysql_connect .mysql_query方法来连接查询数据库时,如果过滤不严就有SQL注入风险,导致网站被攻击. 虽然可以用mysql_real_escape_string ...