学而思编程周赛入门初赛组 | 2026年春第12周
欢迎大家订阅我的专栏:算法题解:C++与Python实现!
本专栏旨在帮助大家从基础到进阶 ,逐步提升编程能力,助力信息学竞赛备战!
专栏特色
1.经典算法练习:根据信息学竞赛大纲,精心挑选经典算法题目,提供清晰的代码实现与详细指导,帮助您夯实算法基础。
2.系统化学习路径:按照算法类别和难度分级,从基础到进阶,循序渐进,帮助您全面提升编程能力与算法思维。
适合人群:
- 准备参加蓝桥杯、GESP、CSP-J、CSP-S等信息学竞赛的学生
- 希望系统学习C++/Python编程的初学者
- 想要提升算法与编程能力的编程爱好者
附上汇总贴:学而思编程周赛入门初赛组 | 汇总
单选题
第1题
根节点深度为0,一棵深度为h的满k(k>1)叉树,即除最后一层无任何子节点外,每一层上的所有结点都有k个子结点的树,共有( )个结点。
A.( k h + 1 − 1 ) / ( k − 1 ) (k^{h+1}-1)/(k-1)(kh+1−1)/(k−1)
B.k h − 1 k^h-1kh−1
C.k h k^hkh
D.( k h − 1 ) / ( k − 1 ) (k^{h-1})/(k-1)(kh−1)/(k−1)
【答案】:A
【解析】
等比数列求和公式:S n = a 1 ( q n − 1 ) q − 1 S_n = \frac{a_1(q^n-1)}{q-1}Sn=q−1a1(qn−1),这里公比为k,S n = 1 ∗ ( k h + 1 − 1 ) k − 1 S_n = \frac{1*(k^{h+1}-1)}{k-1}Sn=k−11∗(kh+1−1)
第2题
在含有n nn个元素的双向链表中查询是否存在关键字为k kk的元素,最坏情况下运行的时间复杂度是( )。
A.O ( 1 ) O(1)O(1)
B.O ( l o g n ) O(logn)O(logn)
C.O ( n ) O(n)O(n)
D.O ( n 2 ) O(n^2)O(n2)
【答案】:C
【解析】
链表支持O(1)删除和插入,但是查询是 O(n) 的。
第3题
某人射击8枪,命中4枪,恰好有三枪连续命中,有多少种不同的情况?( )
A. 5
B. 10
C. 20
D. 40
【答案】:C
【解析】
将三连击看作一个整体,那么问题就转换为一共6枪,其中两枪没有命中的方案数,考虑插空法,将三连击的整体和剩余的一次命中插入四个未命中产生的五个空格中,同时三连击和单击可以交换位置,所以一共是C 5 2 A 2 2 = 20 C_5^2A_2^2=20C52A22=20
在含有n nn个元素的双向链表中查询是否存在关键字为k kk的元素,最坏情况下运行的时间复杂度是( )。
A.O ( 1 ) O(1)O(1)
B.O ( l o g n ) O(logn)O(logn)
C.O ( n ) O(n)O(n)
D.O ( n 2 ) O(n^2)O(n2)
【答案】:C
【解析】
链表支持O(1)删除和插入,但是查询是 O(n) 的。
第4题
以下代码段中输出结果应该是( )。
inta[5]={1,2,3,4,5};int*p=&a[0];cout<<(*p)++<<endl;A. 1
B. 2
C. 3
D. 4
【答案】:A
【解析】
首先,初始化整型数组 a,其中 a[0]=1。接着,定义指针变量p指向数组首元素 a[0] 的地址,此时*p的值等于a[0],即1。在执行语句cout<<(*p)++时,涉及到了后置自增运算符++。根据后置自增运算符"先参与运算,后进行自增”的规则,程序会先取出当前 (*p) 的值(即1)进行输出。输出完成后,再将指针p所指向的内存单元(即a[0])的值加1,使其变为2。因此,该代码段最终输出的结果是1,选项A正确
第5题
下述错误的是( ):
A. 已知一棵二叉树的先序遍历与中序遍历,可以确定二叉树结构。
B. 已知一棵二叉树的后序遍历与中序遍历,可以确定二叉树结构。
C. 已知一棵二叉树的层次遍历与中序遍历,可以确定二叉树结构。
D. 已知一棵二叉树的先序遍历与后序遍历,可以确定二叉树结构。
【答案】:D
【解析】
只知道先序与后序,无法确定树结构。
阅读程序题
#include<bits/stdc++.h>usingnamespacestd;charch;intkey[1000],mw[1000],totm,totk,temp;boolacaps[1000];intmain(){string str1;cin>>str1;for(inti=0;i<str1.length();i++){ch=str1[i];if(ch>='a'&&ch<='z')// 如果是小写ch+=('A'-'a');// 转为大写if(ch>='A'&&ch<='Z'){// 如果是大写key[totk++]=ch-'A';// 转为大写对应的顺序,'A'为0,'Z'为25,并放入到key数组中,totk记录大写字母数量}elsebreak;// 遇到非字母的直接退出循环}string str2;cin>>str2;for(inti=0;i<str2.length();i++){ch=str2[i];if(ch>='a'&&ch<='z'){// 如果是小写acaps[totm]=1;// acaps的totm位置置为1(即记录当前位置是小写还是大写,1为小写)ch+=('A'-'a');// 转为大写}if(ch>='A'&&ch<='Z'){// 如果是大写mw[totm++]=ch-'A';// 转为大写对应的顺序,'A'为0,'Z'为25,并放入到mw数中,totm自增1}elsebreak;// 遇到非字母的直接退出循环}for(inti=0;i<totm;i++){// 在str2的大写字母数量范围内temp=(mw[i]+26-key[i%totk])%26;// 计算temp数字cout<<(char)(temp+(acaps[i]?'a':'A'));// 将temp转为字符并输出}cout<<endl;}第6题
将第13行的if语句改为else if语句不会对程序运行结果有影响( )。
A. 对
B. 错
【答案】:B
【解析】
第11行判断小写后转大写,第13要基于大写字母进行key数组的设置,所以不能用else if,否则会对结果造成影响2
第7题
mw数组与key数组中的值不会超过25。( )
A. 对
B. 错
【答案】:A
【解析】
key和mw数组均为记录大写字母对应的字母顺序,从0~25
第8题
第33行中,若acaps[i]的值为0,则(acap[i]?‘a’:‘A’)的值为’A’。( )
A. 对
B. 错
【答案】:A
【解析】
三目运算符,acaps[i]为false时,执行后半句
第9题
输入字符串为“ab”和“abcdEFG”,则输出为( )。
A. aabbEEH
B. aabbEEG
C. aaccEEH
D. aaccEEG
【答案】:D
【解析】
按照代码模拟,结果选D
第10题
如果输入的两个字符串分别为"CompleteVictory"和"Yvqgpxaimmklongnzfwpvxmniytm",则输出为( )。
A. Wherethereisawillthereisaway
B. Jazzmusiccfeelsabsolutelycool
C. Knowledgeexpandshorizonsgreatly
D. Fantasticjourneysawaitthebrave
【答案】:A
【解析】
只需做第一个字母的判断,就可以选出正确答案,选A
完善程序题
在n ∗ m n*mn∗m的棋盘上放置k kk个国王,要求k kk个国王互相不攻击,有多少种不同的放置方案。假设国王放置在第( x , y ) (x,y)(x,y)格,国王攻击范围区域是( x − 1 , y − 1 ) (x-1,y-1)(x−1,y−1),( x − 1 , y ) (x-1,y)(x−1,y),( x − 1 , y + 1 ) (x-1,y+1)(x−1,y+1),( x , y − 1 ) (x,y-1)(x,y−1),( x , y + 1 ) (x,y+1)(x,y+1),( x + 1 , y − 1 ) (x+1,y-1)(x+1,y−1),( x + 1 , y ) (x+1,y)(x+1,y),( x + 1 , y + 1 ) (x+1,y+1)(x+1,y+1)。读入三个数,n , m , k n,m,kn,m,k,输出答案。题目利用回溯法求解,棋盘行标号为0 ∼ n − 1 0 \sim n-10∼n−1,列标号0 ∼ m − 1 0 \sim m-10∼m−1。
#include <bits/stdc++.h> using namespace std; int n,m,k,ans; int hash[5][5]; void work(int x, int y, int tot) { // x代表行,y代表列 int i, j; if (tot==k) { // 如果放了k个国王(tot初始应为0) ans++; // 方案数加1 return ; } do { while (hash[x][y]>0) { // 当在攻击范围内,就不能放国王了 y++; if (y==m) { // y到了最后一列 x++; // 进入下一行 y = __1__; // 列要从头开始,即为0 } if (x==n) // 如果超过了n-1行则返回 return ; } for (i=x-1; i<=x+1; i++) // 枚举国王攻击范围 if (i>=0 && i<n) for (j=y-1; j<=y+1; j++) if (j>=0 && j<m) __2__; // hash[i][j]++,让其大于0 __3__; // 放下一个国王,work(x,y,tot+1) for (i=x-1; i<=x+1; i++) // 回溯操作 if (i>=0 && i<n) for (j=y-1; j<=y+1; j++) if (j>=0 && j<m) __4__; // 上面是++,这里就是-- y++; if (y==m) { // 到了最后一列 x++; // 进入下一行 y = 0; } if (x==n) // 超过n-1行则返回 return; } while (1); // 死循环 } int main() { cin >> n >> m >> k; ans = 0; memset(hash, 0, sizeof(hash)); __5__; // 函数调用,从头开始遍历,即work(0,0,0) cout << ans << endl; return 0; }第12题
1处应该填( )
A.0
B.1
C.x
D.hash[x][y]
【答案】:A
【解析】
到了下一行,列要从头开始
第13题
2处应该填( )
A.hash[i][j]++
B.hash[i][j]--
C.hash[i][j]=0
D.hash[i][j]=1
【答案】:A
【解析】
如果选D,回溯时hash[i][j]会变为0,对于某个点同时被多个国王攻击的情况,这样就会出错。
第14题
3处应该填( )
A.work(x+1,y,tot+1)
B.work(x,y+1,tot+1)
C.work(x+1,y+1,tot+1)
D.work(x,y,tot+1)
【答案】:D
【解析】
从当前位置继续搜索
第15题
4处应该填( )
A.hash[i][j]++
B.hash[i][j]--
C.hash[i][j]=0
D.hash[i][j]=1
【答案】:B
与第13题相对,这里是–
第1题
5处应该填( )
A.work(n,m,0)
B.work(n,m,k)
C.work(0,0,0)
D.work(1,1,1)
【答案】:C
【解析】
从头开始扫描,初始方案数为0
