2017/10/12 NOIp模拟赛
概述
我从未写过模拟赛的题解,但是这次模拟赛全部是原题,因此写公开题解也不会有版权问题。所有题目2s,512MB。
prmq
来源
codechef June17 Chef and Prime Queries
题意
给定$N$($N\le10^5$)个数$A_{1\dots N}$($2\le A_i\le 10^6$),$Q$($Q\le10^5$)个询问$L,R,X,Y$($1\le L\le R\le N,1\le X\le Y\le 10^6$),求$A_{L\dots R}$中的数包含$X\dots Y$中的质因数的总数。
样例
1 | 4 |
1 | 4 |
子任务
- 30%:$N,Q\le100,X,Y,A_i\le1,000$
- 50%:$N,Q\le1,000,X,Y,A_i\le10,000$
- 100%:$N,Q\le10^5$
题解
30%
在原题和模拟赛中都提供了一个代码片段,将其实现加上$O(\sqrt V)$的质数判断即可得到30%。时间复杂度$O(QVN\log V)$
50%
可以发现每个数的不同质因数的数量是相当有限的,具体的,对于$A_i\le10^6$,最多只有7个不同的质因数(2*3*5*7*11*13*17=510,510)。因此对每个数分解质因数,每次扫描$A_{L\dots R}$统计合法的质因数个数。时间复杂度$O(N\sqrt V+QN)$,当然第二项要*7。
100%
进一步,这其实就是一个二维数点问题,一维是$L\dots R$,另一维是$X\dots Y$。这两维范围并不大,所以不需要离散化,可以用树套树,也可以用主席树^ptree。模拟赛时,我还想到了莫队,但好像难以实现;有人写了,但只有暴力分。我用了半个多小时写完了好久没写的主席树,还写了欧拉筛,调到一个小时过了样例。然后又很快写了一下对拍,没有错误。时间复杂度$O(V+N(\sqrt V+\log V)+Q\log V)$,空间复杂度$O(N\log V)$。实际上,不需要$O(V)$欧拉筛,直接质因数分解也可以。
1 |
|
但是,上课曾经讲过二维数点可以离线解决。这题最方便的写法是将询问拆成$(R,X,Y)-(L-1,X,Y)$,排序,用树状数组维护每个质因数出现的次数即可。时间复杂度$O(N(\sqrt V+\log V)+Q\log V)$,空间复杂度$O(V+Q)$,比主席树更简单。
得分
0 | 20 | 30 | 50 | 100 | 平均分 |
---|---|---|---|---|---|
7 | 4 | 2 | 12 | 8 | 47 |
这题的思路比较简单,只要写数据结构,是平均分最高的一题。
ants
来源
AtCoder Grand Contest 013C Ants on a Circle
题意
在一个周长为$L$($L\le10^9$)的圆上有$N$($N\le10^5$)只蚂蚁,每只蚂蚁初始位置为$X_i$($X_i\in\mathbb{N},0\le X_i<L$),方向$W_i$($W_i\in{1,2}$,1为顺时针,2为逆时针)。每只蚂蚁在单位时间内移动单位距离,两只蚂蚁相撞会立即掉头,求$T$($T\le10^9$)时刻每只蚂蚁对应的位置。
样例
1 | 3 8 3 |
1 | 1 |
子任务
- 30%:$T\le100$
- 另30%:$X_1-T\ge0,X_N+T<L$
- 100%:$0\le X_1<X_2\dots<X_N<L$
题解
很容易发现,我们可以计算出所有蚂蚁的最终位置,因为两只蚂蚁相撞可以看作直接对穿而过。因此只要确定每只蚂蚁最终位置的对应关系。
30%
找不到对应关系,但还是可以直接模拟这个过程的。简单起见,把坐标乘以2,这样只会在整数时刻相撞,模拟$2T$时间,一直保持坐标的有序性。这样模拟是比较难写的,时间复杂度$O(NT)$。在模拟赛中,我在这题上花了很多时间,写了一个$O(TN\log N)$的模拟,但最终0分。
另30%
这种情况下不会绕圈,可以发现蚂蚁相撞后,其排名没有改变。只要把最终位置排序,就与初始位置是一一对应的。这里的30%比上述简单多了,时间复杂度$O(N\log N)$。这个问题很经典,可以在洛谷P1367交,注意不同的是蚂蚁没有排序,需要先进行排序。
100%
如果蚂蚁可以绕圈,会发生什么呢?只要确定排名为1的蚂蚁在最终位置中的编号。如果一只蚂蚁顺时针穿过了$X=0$,可以发现排名为1的蚂蚁在最终编号中+1,就是样例的情况;反之亦然。因此,我们可以根据每只蚂蚁穿过$X=0$的次数计算出排名为1的蚂蚁在最终位置中的标号。时间复杂度$O(N\log N)$
1 |
|
得分
0 | 30 | 60 | 100 | 平均分 |
---|---|---|---|---|
24 | 5 | 2 | 2 | 14 |
这题的思路比较巧妙,而模拟比较难写,是得分最低的。
piling
来源
AtCoder Grand Contest 013D Piling Up
题意
盒子里有无限多的红色和蓝色积木,先任意取出$N$($N\le3,000$)块,再进行$M$($M\le3,000$)次以下操作来搭$2M$高的塔:
- 将任意一块积木放在塔上
- 取出一块红色积木和一块蓝色积木
- 将任意一块积木放在塔上
样例
1 | 2 3 |
1 | 56 |
子任务
- 30%:$N,M\le5$
- 50%:$N,M\le100$
- 100%:$1\le N,M\le3,000$