天天快乐编程2020年OI集训队 训练4-提高组题解

本次比赛题目为2019CSP认证S组原题,去年浙江S组入围线72.5分,共1148名,有效参加共2153人。

一、单项选择

1. 答案:D

解析:x+y转整数等于7,取模运算与乘法优先级一样,所以7%3*7%2=1

2. 答案:C

解析:WMV是音频、MPEG、AVI是视频、JPEG是图像。

3. 答案:D

解析:或运算,有1得1,将两个数字进行右对齐,14进行或运算均为1。

4. 答案:B

解析:编译器将高级语言(例如C++、java、pascal等人类比较容易看的懂的)翻译成低级语言(机器语言,方便机器执行,因为机器只认识01)。

5. 答案:B

解析:x的类型是float, 所以(x*100+0.5)也是float, 也就是有小数位,需要先转黄成int格式, 也就是B选项。

6. 答案:B

解析:暴力枚举
1.当取出1,1,2,4时,共有C(2,4)*2=12种;
2.当取出1,1,2,8,也是12种;
3.当取出1,1,4,8,也是12种;
4.当取出1,1,8,8,为C(2,4)是6种;
5.当取出为1,2,4,8,为A(4,4)=20 种;
6.当取出1,2,8,8,为12种;
7.当取出1,4,8,8为12种,
8.当取出2,4,8,8为12种。
一共102种情况。
这个题目比较难

7. 答案:C

解析:稳定排序就是记录的相对次序保持不变。
快速排序判断的有相等的元素,很有可能把前面的元素的稳定性打乱。比如序列为 5 3 3 4 3 8 9 10 11, 现在头指针元素5和3(第5个元素,下标从1开始计)交换就会把元素3的稳定性打乱,所以快速排序是一个不稳定的排序算法,不稳定发生在头指针元素和a[j] 交换的时刻。
堆排序、快速排序、希尔排序、直接选择排序是不稳定的排序算法,而基数排序、冒泡排序、直接插入排序、折半插入排序、归并排序是稳定的排序算法。
这个题目如果不了解也不好做

8. 答案:B

解析:完全图边数=n*(n-1)/2。于是28条边的联通图至少需要8个点,但是本题说的是非联通图,再多加一个孤立点,8+1=9。

9. 答案:B

解析:前2位有0,1,8,6,9,5种选择,第3位只能放0,1,8,后2位由前2位决定。而0,1,8模3正好余0,1,2,所以给定其他4位,第3位有且仅有1种选择,总数=55111=25。
这个题目比较难

10. 答案:A

解析:容斥原理,总满分人数=数学满分+语文满分-语文数学满分=15+12-4=23。

11. 答案:D

解析:一个数组被取完后就不需要比较了,所以最好情况n次最坏情况2n-1。

12. 答案:D

解析:邻接矩阵和邻接表可以存储图,其他三项都是数据结构,不是存储结构。

13. 答案:B

解析:Dijkstra算法需要每次选取d[i]最小的边;Prim算法需要每次选在集合E中选取权值最小的边;kruskal剩下的所有未选取的边中,找最小边。Floyd是动态规划不是贪心。

14. 答案:B

解析:设公比是p,那么2 * p ^ (2n-2)=118098, 2 * p ^ (n-1)=486,可以得到p^(n-1)=243,由于gcd(2,243)=gcd(4,243)=gcd(5,243)=1,所以排除2,4,5,而gcd(3,243)=3,所以公比可能是3。

15. 答案:A

解析:数字三角形原题。每个点的只能够从C(i-1,j-1)以及C(i-1,j)过来,所以最优解肯定是从更大的那个节点到,所以结果包含max(C(i-1,j-1), C(i-1,j)), 而计算的是和所以也包含aij这一项。

二、阅读程序

16. 12行if判断如a[i]比前一位小,则从i开始,否则从上次开始14行while循环找ans向后找第一个>a[i]的数12行的判断的意思是,如果后项<=前项,则重新开始,否则从上项开始。整个程序含义是找每个a[i]后第一个大于a[i]的位置。

1)答案:错

解析:12行if成立,14行while不成立,则16行ans==i

2)答案:对

解析:13行i<=n,15行ans<n才会自增,所以不会超过n

3)答案:对

解析:12行只是一个优化,删掉会变慢

4)答案:对

解析:14行,由于ans是第一个大于a[i]的,所以a[i+1]..a[ans-1]都不超过a[i],结论成立

5)答案:D

解析:单调增,则12行if不会成立,也就是ans只增不减所以复杂度为O(n)

6)答案:A

解析:最坏情况下,12行if总是成立(a单调减)此时14行也会一直运行到ans=n,复杂度为1+2+..+n=O(n^2)

17.利用并查集,而且并查集没有进行路径压缩,记录下了深度

1)答案:对

解析:并查集初始化下标是[0,n-1]

2)答案:错

解析:并查集初始化自己的爸爸是他自己,findRoot里也有fa[v]==v

3)答案:对

解析:fa[i]表示i的父亲,下标也在0~n-1范围内

4)答案:错

解析:a和b相等时,cnt[i]的值翻倍,会超出n

5)答案:C

解析:每两次合并x和y都不同,表示每次都是单独一个去和整体合并。此时cnt[y]增加cnt[x]的值,也就是加1。11+12+...149=5049/2=1225

6)答案:C

解析:并查集getRoot函数没有路径压缩,单次查找最坏为O(n),压缩后效率是logn。总效率为O(n^2)

18.从s中删去若干个字符,可以得到t。这个题目比较困难。可以采用“代入简单数据”的大法,画一个表,来看一下每一行代码的作用。

1)答案:对

解析:suf[i]是满足t[suf[i]+1..tlen-1]为s[i..slen-1]子序列的最小值

2)答案:错

解析:题目的输出为s中删去连续多少个字母后t仍然是s的子序列;,两者相等时结果为0。

3)答案:错

解析:第一轮执行22行时tmp=0,j=0不执行,因此这轮j-i-1就可能是负数。

4)答案:错

解析:如果t是s的子序列,那么0~pre[i]-1,suf[i+1]+1~lent-1这部分分别是s[0 ~ i],s[i+1 ~ lens-1]的子序列,不会重叠,所以有pre[i]-1<suf[i+1]+1,也就是pre[i]<=suf[i+1]+1

5)答案:D

解析:slen是s的长度,至少需要输入一个长度的字符串,如果t不是s子序列那输出一定是0

6)答案:C

解析:输出是2说明s串删去两个连续元素后t仍是s的子序列,因此删去后长度至少为10,删前至少为12

三、完善程序

19.本题属于一个模拟题,不过完善程序已经变为选择题,还是好做多了。

1)答案:C

解析:unlock作用是看是否能解锁任务。根据对问题5的分析,在未解锁前它的值是还有几个依赖任务未解锁。那么解锁条件当然是0个依赖任务,因此是等于0

2)答案:D

解析:解锁条件二,经验点要大于等于任务的需求点

3)答案:D

解析:可以推测出这里进行经验累加的地方,其他三个也可以通过排除法进行排除。

4)答案:C

解析:从前面分析看出unlock是依赖的还没解锁的任务数,解锁一个任务,所有依赖这个任务的unlock值都要减1

5)答案:B

解析:m是任务依赖的任务数,从前面代码看出当unlock[i]为-1时表示解锁成功,那么D不对。A的话cnt[i]此时还没完成赋值,也不对。C有迷惑性,认为unlock是布尔值,但看题目m个依赖任务完成才能解锁该任务,所以不是单纯的布尔,需要每解锁一个前置任务就将unlock减1,直到为0

20.首先使用f(i)表示有i个石子时,是否有必胜策略。所以f(i)=!f(i-b[j1]) or !f(i-b[j2]) ...) (a[j]<=i), 转换公式,status中每一位定义为win(i-j), 也就是有i-j有必胜策略。这个题目比较新潮,是NIM博弈,而且还有状态压缩,据说本题是很多人的第一次状压。但是部分题目还是可以猜出答案。

1)答案:C

解析:第一空需要填写初始状态,石子有0个,怎么样都是输的。然后trans相当于记录当前状态下能够必胜的策略位置也就是b[j]的集合。

2)答案:B

解析:能转移的状态数不会减少

3)答案:A

解析:将b[j]加到trans里面(记录新增的能够必胜的位置)

4)答案:D

解析:要往status记录新的必胜策略的位置

5)答案:D

解析:当前状态下能走到的先手必输的情况不为空。要将status状态更新,具体就是将当前的win记录到status的最低位上即可

原文地址:https://www.cnblogs.com/BobHuang/p/13757882.html