把博客园图标替换成自己的图标
把博客园图标替换成自己的图标end

题解P8084 [COCI2011-2012#4] BROJ

P8084 [COCI2011-2012#4] BROJ

题意

非常清晰,所以就不多讲了。

思路

其实部分分给予了一部分的思路:
对于 $P$ 大时,与 $P$ 小时,我们可以分开考虑。

  1. 可以迅速解决的特判:
    1. $K=1$,输出 $P$。
    2. $K\times P>1e9$,输出 0。
    3. $P\times P>1e9$,输出 0。
  2. 当 $P$ 较大时,我们只需从 $P\times P$ 开始枚举 $P$ 的倍数,并且除上小于 $P$ 的质数。

伪代码如下:

init(P-1);//素数筛,筛出小于P的质数
for(int i=P; i*P<=(int)1e9; ++i) {
    ......
}
  1. 当 $P$ 较小时,我们可以用一小点容斥,就可以快速求解。

优化

当我们在打上面的第二项时,可以发现,$i<10^9/P$(非常显然~)。
所以,实际上我们素数筛并不需要筛到 $P-1$,只需到 $\min \left \{ P-1 ,10^9/P\right\}$,就可以了。
于是我们的复杂度就又下降了一个档次,以至于当 $P=5$ 时,时间复杂度可以几近 $4\times 10^8$,可以通过时间限制。
于是就十分愉快的可以去掉容斥,而用特判代替:

if(P==2) {
    if(K*2<=1e9) cout<<2*K<<endl;
    else cout<<0<<endl;
} else if(P==3) {
    if(1ll*6*K-3<=1e9) cout<<6*K-3<<endl;
    else cout<<0<<endl;
}

卡常小细节:在素数筛时,不要用 vector,最好用数组,否则极限时间下可能会变 TLE。

posted @ 2023-02-26 19:56  djh0314  阅读(23)  评论(0)    收藏  举报  来源
浏览器标题切换
浏览器标题切换end