当前位置:网站首页>数论分块(整除分块)
数论分块(整除分块)
2022-04-23 06:21:00 【Zimba_】
前言:
断更太久,已经忘了博客怎么写了。。
这篇博客用来介绍带整除式子的快速求解办法。
符号说明:
⌊ a b ⌋ \left \lfloor \frac{a}{b}\right \rfloor ⌊ba⌋ : a a a除以 b b b向下取整。
⌈ a b ⌉ \left \lceil \frac{a}{b}\right \rceil ⌈ba⌉ : a a a除以 b b b向上取整。
∑ i = 1 n f ( i ) \sum_{i=1}^{n}f(i) ∑i=1nf(i) : 累加符号,表示 f ( 1 ) + f ( 2 ) + … + f ( n ) f(1)+f(2)+…+f(n) f(1)+f(2)+…+f(n)。
问题:
求解 ∑ i = 1 n ⌊ n i ⌋ \sum_{i=1}^{n}\left \lfloor \frac{n}{i}\right \rfloor ∑i=1n⌊in⌋,其中 1 ⩽ n ⩽ 1 e 12 1\leqslant n \leqslant 1e12 1⩽n⩽1e12。
正文:
首先,不难发现有一个o(n)的暴力。
我们需要一个 n \sqrt{n} n的做法。
我们可以先举例观察,我们举 n = 10 n=10 n=10,然后枚举从 1 1 1到 n n n枚举 i i i,观察 ⌊ n i ⌋ \left \lfloor \frac{n}{i}\right \rfloor ⌊in⌋的值。
1 1 1 2 2 2 3 3 3 4 4 4 5 5 5 6 6 6 7 7 7 8 8 8 9 9 9 10 10 10
10 10 10 5 5 5 3 3 3 2 2 2 2 2 2 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1
就是上面这个样子。
不难发现也不难证明,相同的数都是连续的,可以把它分成一块一块值相同的段。那么我们可以利用这个性质,对于每一块,将这个块的数字乘上块的长度,就可以求解这一块的和了。
现在还有两个问题要解决。
一个是块的数量,一个是如何快速找到块的两端。
首先块的数量,对于 i i i从 1 1 1到 n n n取值, ⌊ n i ⌋ \left \lfloor \frac{n}{i}\right \rfloor ⌊in⌋的值的种数不会超过 2 n 2\sqrt{n} 2n,也就是块的数量不会超过 2 n 2\sqrt{n} 2n。
证明其实很容易,
嗯,可以证,前 n \sqrt{n} n个 i i i最多有 n \sqrt{n} n种值,而当 i i i大于 n \sqrt{n} n时,取值一定小于 n \sqrt{n} n,所以不超过 2 n 2\sqrt{n} 2n(摘自ztc口糊)。
那么第二个问题,快速找到块的端点。
当某一块的左端点为 l l l,那么它的右端点 r r r就是 ⌊ n ⌊ n l ⌋ ⌋ \left \lfloor \frac{n}{\left \lfloor \frac{n}{l}\right \rfloor}\right \rfloor ⌊⌊ln⌋n⌋。 这个就更好证了。
也可以理解成,已知 i i i,那么与 i i i相同的块的右端点就是 ⌊ n ⌊ n i ⌋ ⌋ \left \lfloor \frac{n}{\left \lfloor \frac{n}{i}\right \rfloor}\right \rfloor ⌊⌊in⌋n⌋
也就是说,当 i i i的取值在 l l l到 r r r之间时,式子的结果是一样的,那么只要再乘上区间长度 ( r − l + 1 ) (r-l+1) (r−l+1)即可。
最后再对于原问题,上模板代码:(有取模的加取模)
ll ans=0;
for(ll l=1,r;l<=n;l=r+1)
{
r=n/(n/l);
ans+=(r-l+1)*(n/l);
}
例题及应用:
再拓展几个例题,有,但不全,还是要去多找题做。
问题1:
已知 w w w和 n n n,求解 ∑ i = 1 n ⌊ w i ⌋ \sum_{i=1}^{n}\left \lfloor \frac{w}{i}\right \rfloor ∑i=1n⌊iw⌋,其中 1 ⩽ n , w ⩽ 1 e 12 1\leqslant n,w \leqslant 1e12 1⩽n,w⩽1e12。
解:
与原题不同,这里的枚举上界 n n n不再作为被除数。
那么在计算右端点 r r r的时候,会引发一个细节问题。
看式子, r = w / ( w / l ) r=w/(w/l) r=w/(w/l)。会出现两个种特殊情况。
一种是 w / l = = 0 w/l==0 w/l==0,此时再调用这个式子就会出现除 0 0 0的情况,导致RE。
还有一种是,计算结果 r > n r>n r>n,此时右端点不在边界内了。
要把这两种情况考虑进去,在原代码的基础上进行修改。
ll ans=0;
for(ll l=1,r;l<=n;l=r+1)
{
if(w/l)r=w/(w/l);
else r=n;
r=min(r,n);
ans+=(r-l+1)*(w/l);
}
问题2:
已知 a , b a,b a,b和 n n n,求解 ∑ i = 1 n ⌊ a i ⌋ ⌊ b i ⌋ \sum_{i=1}^{n}\left \lfloor \frac{a}{i}\right \rfloor\left \lfloor \frac{b}{i}\right \rfloor ∑i=1n⌊ia⌋⌊ib⌋,其中 1 ⩽ n , a , b ⩽ 1 e 12 1\leqslant n,a,b \leqslant 1e12 1⩽n,a,b⩽1e12。
解:
在原问题的基础上多乘了一个,不过别怕,只不过从原来 2 a 2\sqrt{a} 2a个断点,变成了 2 a + 2 b 2\sqrt{a}+2\sqrt{b} 2a+2b个断点,复杂度仍然是根号级别的。
我们只要每次找最近的那个断点即可。
ll ans=0;
for(ll l=1,r,r1,r2;l<=n;l=r+1)
{
if(a/l)r1=a/(a/l);
else r1=n;
if(b/l)r2=b/(b/l);
else r2=n;
r=min(r1,r2)
r=min(r,n);
ans+=(r-l+1)*(a/l)*(b/l);
}
问题3:
已知 w w w和 n n n,求解 ∑ i = 1 n ⌈ w i ⌉ \sum_{i=1}^{n}\left \lceil \frac{w}{i}\right \rceil ∑i=1n⌈iw⌉,其中 1 ⩽ n , w ⩽ 1 e 12 1\leqslant n,w \leqslant 1e12 1⩽n,w⩽1e12。
解:
这是向上取整的,不好找到想原来一样的结论,但是我们可以把向上取整转化为向下取整。
⌈ w i ⌉ = ⌊ w + i − 1 i ⌋ = ⌊ w − 1 i ⌋ + 1 \left \lceil \frac{w}{i}\right \rceil=\left \lfloor \frac{w+i-1}{i}\right \rfloor=\left \lfloor \frac{w-1}{i}\right \rfloor+1 ⌈iw⌉=⌊iw+i−1⌋=⌊iw−1⌋+1
就可以轻松解决了。
ll ans=0;
for(ll l=1,r;l<=n;l=r+1)
{
if((w-1)/l)r=(w-1)/((w-1)/l);
else r=n;
r=min(r,n);
ans+=(r-l+1)*((w-1)/l+1);
}
问题5:
已知 w w w和 n n n,求解 ∑ i = 1 n i ⌊ w i ⌋ \sum_{i=1}^{n}i\left \lfloor \frac{w}{i}\right \rfloor ∑i=1ni⌊iw⌋,其中 1 ⩽ n , w ⩽ 1 e 12 1\leqslant n,w \leqslant 1e12 1⩽n,w⩽1e12。
解:
多乘了一个 i i i,与原来不同的就是,这次我们不能再乘 r − l + 1 r-l+1 r−l+1了,前面 r − l + 1 r-l+1 r−l+1的本质其实是那一段的区间和,这时候我们要乘上的是区间 i i i的求和。(因为这段区间里 ⌊ w i ⌋ \left \lfloor \frac{w}{i}\right \rfloor ⌊iw⌋是一样的,相当于一个常系数,所以才可以这么乘的)
ll ans=0;
for(ll l=1,r;l<=n;l=r+1)
{
if(w/l)r=w/(w/l);
else r=n;
r=min(r,n);
ans+=(r-l+1)*(l+r)/2*(w/l);
}
问题6:模和积
求 ∑ i = 1 n ∑ j = 1 m ( n m o d i ) × ( m m o d j ) , i ≠ j \sum_{i=1}^{n}\sum_{j=1}^{m}(n\;mod\;i)\times (m\;mod\;j),i\neq j ∑i=1n∑j=1m(nmodi)×(mmodj),i=j模 19940417 19940417 19940417的值。
其中 1 ⩽ n , m ⩽ 1 e 9 1\leqslant n,m \leqslant 1e9 1⩽n,m⩽1e9。
解:
首先要知道 ( n m o d i ) = n − i × ⌊ w i ⌋ (n\;mod\;i)=n-i\times \left \lfloor \frac{w}{i}\right \rfloor (nmodi)=n−i×⌊iw⌋。
然后开始化式子,注意 i ≠ j i\neq j i=j的条件不能忽略。

化好公式后,就可以写了。
#include<bits/stdc++.h>
#include<unordered_map>
using namespace std;
typedef long long ll;
const ll mod=19940417;
typedef pair<int,int> P;
const ll MAXN=1000000;
const ll inv6=3323403;
ll sum(ll l,ll r,ll flag)
{
if(flag==1)
{
return (r-l+1)*(l+r)/2%mod;
}
else
{
return (r*(r+1)%mod*(2*r+1)%mod*inv6%mod-(l-1)*l%mod*(2*l-1)%mod*inv6%mod+mod)%mod;
}
}
int main()
{
ll n,m;
scanf("%lld%lld",&n,&m);
ll sum1=0;
for(ll l=1,r;l<=n;l=r+1)
{
r=n/(n/l);
sum1=(sum1+n*(r-l+1)%mod-sum(l,r,1)*(n/l)%mod+mod)%mod;
}
ll sum2=0;
for(ll l=1,r;l<=m;l=r+1)
{
r=m/(m/l);
sum2=(sum2+m*(r-l+1)%mod-sum(l,r,1)*(m/l)%mod+mod)%mod;
}
ll nm=min(n,m);
ll sum3=0;
for(ll l=1,r,r1,r2;l<=nm;l=r+1)
{
if(n/l)r1=n/(n/l);
else r1=nm;
if(m/l)r2=m/(m/l);
else r2=nm;
r=min(r1,r2);
r=min(r,nm);
sum3=(sum3+n*m%mod*(r-l+1)%mod-(n*(m/l)%mod+m*(n/l)%mod)*sum(l,r,1)%mod+sum(l,r,2)*(n/l)%mod*(m/l)%mod+mod)%mod;
}
ll ans=(sum1*sum2-sum3+mod)%mod;
printf("%lld\n",ans);
return 0;
}
问题7:余数求和
解:
问题6的简化版本,就不贴代码了。
版权声明
本文为[Zimba_]所创,转载请带上原文链接,感谢
https://blog.csdn.net/weixin_43785386/article/details/104410046
边栏推荐
猜你喜欢

关于'enum'枚举类型以及结构体的问题。

自定义classloader并实现热部署-使用loadClass

USO technology was invited to share the technical framework and challenges of AI synthetic virtual characters at lvson2020 conference

数据分析入门 | kaggle泰坦尼克任务(四)—>数据清洗及特征处理

可视化常见问题解决方案(八)共享绘图区域问题解决方案

江宁医院DMR系统解决方案

学习笔记6-几种深度学习卷积神经网络的总结

可视化之路(十一)matplotlib颜色详解

可视化常见问题解决方案(八)数学公式

Emergency air space integrated communication system scheme of Guangxi Power Grid
随机推荐
Tensorflow安装后ImportError: DLL load failed: 找不到指定的模块,且国内安装缓慢
数据分析入门 | kaggle泰坦尼克任务(四)—>数据清洗及特征处理
利用mysql-binlog恢复数据
免费开源农业物联网云平台(Version:3.0.1)
MVCC(多版本并发控制)
什么是闭包?
字节数仓实习生面试sql题
How to improve the service efficiency of the hotel without blind spots and long endurance | public and Private Integrated walkie talkie?
PyTorch 19. Differences and relations of similar operations in pytorch
hql求一个范围内最大值
PyTorch 18. torch. backends. cudnn
el-select 中v-model绑定值,数据回显只显示value,不显示label
Patrol inspection intercom communication system in power industry
Machine vision series (01) -- Overview
PyTorch 17. GPU concurrency
# 可视化常见绘图(二)折线图
anaconda3安装
Emergency medical communication solution | mesh wireless ad hoc network system
LATEX使用
(一)OpenPAI jupyter jupyterhub jupyterlab 方案比较