欢迎大家订阅我的专栏:算法题解:C++与Python实现!
本专栏旨在帮助大家从基础到进阶 ,逐步提升编程能力,助力信息学竞赛备战!
专栏特色
1.经典算法练习:根据信息学竞赛大纲,精心挑选经典算法题目,提供清晰的代码实现与详细指导,帮助您夯实算法基础。
2.系统化学习路径:按照算法类别和难度分级,从基础到进阶,循序渐进,帮助您全面提升编程能力与算法思维。
适合人群:
- 准备参加蓝桥杯、GESP、CSP-J、CSP-S等信息学竞赛的学生
- 希望系统学习C++/Python编程的初学者
- 想要提升算法与编程能力的编程爱好者
附上汇总贴:历年蓝桥杯青少组Python中/高级选拔赛(STEMA)真题解析 | 汇总
选择题
第1题
下列运算符中,优先级最高的是( )
A./
B.%
C.**
D.+
【答案】:C
【解析】
Python运算符的优先级由高到低依次为:
1、括号运算符(())
2、幂运算符(**)
3、一元运算符(+,-)
4、乘法(*),除法(/),取模(%),整除(//)
5、加法(+),减法(-)
6、比较运算符(<,>,<=,>=,==,!=)
7、逻辑运算符(and,or,not)
8、赋值运算符(=,+=,-=,*=,/=,%=,//=,**=)。
第2题
下列数据类型中,哪一个是不可变的?( )
A.列表
B.元组
C.字典
D.集合
【答案】:B
【解析】
列表、字典和集合,都是可以修改的,元组不可修改
第3题
执行以下程序后,输出的结果是( )
L = [1,2,3,4,5,6,7,8,9]
print(L[1:4])
A.[1,2,3]
B.[1,2,3,4]
C.[2,3]
D.[2,3,4]
【答案】:D
【解析】
L[1:4]表示从第1个元素(下标从0开始)遍历到第3个元素,即[2,3,4]
第4题
下列选项描述正确的是( )
A.continue语句可以结束整个循环的执行
B.break和continue语句只能用在循环中
C.要从多层循环嵌套中退出时,只能使用goto语句
D.break和continue语句在循环体内的作用相同
【答案】:B
【解析】
continue不能结束循环,会跳到下一次循环,所以A错误
要从多层循环嵌套中退出时,可以使用goto和return语句,所以C错误
break用于结束循环,所以break和continue在循环体内的作用相同
第5题
以下关于函数参数描述正确的是( )
A.调用函数时,按参数名称传递参数,需要按照定义时的顺序进行传递
B.函数在定义时,可选参数的位置可以在参数列表中任意位置
C.函数在定义时,可以不指定可选参数默认值,在调用函数时候传入参数
D.实参和形参存储在各自的内存空间中,所以是两个不相关的独立变量
【答案】:D
【解析】
使用关键字参数来按照参数名称传递参数,这样就不再需要按照定义时的顺序传递,所以A错误。
def my_function(param1, param2):
print("Param1:", param1)
print("Param2:", param2)
my_function(param2="Hello", param1=42)
必选参数在前,可选参数在后,所以B错误。
默认值参数,是在定义函数时直接为这些参数指定默认值,当函数被调用时,如果没有传入对应的参数值,则使用函数定义的默认值替代,所以C错误。
编程题
第6题
【题目描述】
输入一个整数 N ( − 100 ≤ N ≤ 100 ) N(-100≤N≤100) N(−100≤N≤100),输出 N − 5 N-5 N−5 的结果。
例如: N = 8 N=8 N=8, 8 − 5 8-5 8−5 的结果为 3 ( 3 = 8 − 5 ) 3(3=8-5) 3(3=8−5)
【输入】
输入一个整数 N ( − 100 ≤ N ≤ 100 ) N(-100≤N≤100) N(−100≤N≤100)
【输出】
输出一个整数,表示 N − 5 N-5 N−5 的结果
【输入样例】
8
【输出样例】
5
【解题思路】
【代码详解】
n = int(input()) # 输入数字
print(n-5) # 输出N-5的结果
【运行结果】
8
3
第7题
【题目描述】
给定一个正整数 N ( 2 ≤ N ≤ 1000 ) N(2≤N≤1000) N(2≤N≤1000),请将 N N N 拆分成两个正整数的和,且两个正整数相差最小。
例如:
N = 4 N=4 N=4,拆分成两个相差最小正整数为 2 2 2 和 2 2 2;
N = 5 N=5 N=5,拆分成两个相差最小正整数为 2 2 2 和 3 3 3。
【输入】
输入一个正整数 N ( 2 ≤ N ≤ 1000 ) N(2≤N≤1000) N(2≤N≤1000)
【输出】
第一行输出一个正整数,表示拆分后的两正整数中较小的那个(相同大小输出任意一个)
第二行输出一个正整数,表示拆分后的两正整数中较大的那个(相同大小输出任意一个)
【输入样例】
5
【输出样例】
2
3
【解题思路】
【代码详解】
n = int(input()) # 输入正整数N
a = n//2 # a为N的一半
b = n-a # b为另一半
print(b) # 输出较小的数
print(a) # 输出较大的数
【运行结果】
5
2
3
第8题
【题目描述】
某商店部分产品搞活动,每买两件商品只收取最高价格商品的费用,另一件商品不收取费用(相同价格只收取一件商品费用)。小明选购了 N N N 件( 2 ≤ N ≤ 1000 2≤N≤1000 2≤N≤1000, N N N 为偶数)商品,且已知每件商品的价格,他会每次结算两件商品。请帮助小明计算出N件商品最少花费多少钱。
例如: N = 6 N=6 N=6, 6 6 6 件商品价格分别为 32 32 32、 56 56 56、 92 92 92、 45 45 45、 12 12 12、 98 98 98,可结算 3 3 3 次, 98 98 98 和 92 92 92 的商品一起结算, 56 56 56 和 45 45 45 的商品一起结算, 32 32 32 和 12 12 12 的商品一起结算,共花费 186 ( 186 = 98 + 56 + 32 ) 186(186=98+56+32) 186(186=98+56+32)。
【输入】
第一行输入一个正整数 N N N(2≤N≤1000,N为偶数),表示小明购买了商品数
第二行输入 N N N 个正整数( 1 ≤ 正整数 ≤ 100 1≤正整数≤100 1≤正整数≤100),表示每件商品的价格,正整数之间以一个英文逗号隔开
【输出】
输出一个整数,表示小明购买 N N N 件商品最少需要花费的钱数
【输入样例】
6
32,56,92,45,12,98
【输出样例】
186
【解题思路】
【代码详解】
n = int(input())
a = [int(i) for i in input().split(',')]
a = sorted(a) # 对a列表进行从小到大排序
ans = 0
for i in range(n): # 遍历n个产品
if i%2==1: # 将下标为奇数的商品(即连续2个商品中价格较贵的那件)价格加到总和中
ans += a[i]
print(ans)
【运行结果】
6
32,56,92,45,12,98
186
第9题
【题目描述】
有一个 N ∗ M N* M N∗M 的矩形拼图积木板( 1 ≤ N ≤ M ≤ 15 1≤N≤M≤15 1≤N≤M≤15, N N N 和 M M M 为正整数),和若干个 1 ∗ 1 1*1 1∗1、 2 ∗ 2 2*2 2∗2、 3 ∗ 3 3*3 3∗3…、 10 ∗ 10 10*10 10∗10的正方形积木。使用任意积木将积木板铺满(不能有空隙),请问最少需要几块积木。
例如: N = 3 N=3 N=3, M = 4 M=4 M=4,最少需要 4 4 4 块积木( 1 1 1 块 3 ∗ 3 3*3 3∗3, 3 3 3 块 1 ∗ 1 1*1 1∗1)。
【输入】
输入两个正整数 N N N 和 M ( 1 ≤ N ≤ M ≤ 15 ) M(1≤N≤M≤15) M(1≤N≤M≤15),表示矩形积木板的长和宽,正整数之间以一个空格隔开
【输出】
输出一个整数,表示铺满积木板最少需要的积木数量
【输入样例】
3 4
【输出样例】
4
【解题思路】
【代码详解】
n, m = [int(i) for i in input().split()]
if n>m: # 先调整大小,保证n小于等于m
n,m = m,n
def calc(n, m):
ans = 0
while n!=m: # 当n与m不相等时
if n>m: # 调整大小
n, m = m, n
n = n # 小的那个边不变
m = m-n # 大的边长减去小的边长
ans+=1 # 增加1个积木
ans += 1 # 最后再加上n等于m的1个图形
return ans # 返回计算结果
if n==m and n<=10: # 对于n与m相等,且小于等于10的
print(1) # 只需1个积木
elif n==m and n>10: # 对于n与m相等,且大于10的
print(1 + calc(n-10, 10) + calc(m-10, n)) # 图形被拆成了3部分,分别计算
elif n>10 and m>10: # 对于n与m不相等,且大于10的
print(1+ calc(m-10, n) + calc(n-10, 10)) # 也被拆分3分布(同上一种情况)
elif n<=10 and m>10: # 对于m大于10的
print(1 + calc(m-10, n)) # 图形被拆成了2部分
else: # 其他(n和m都小于10,且不相等的)
print(calc(n, m))
【运行结果】
3 4
4
第10题
【题目描述】
小明有一张矩形彩纸,他将彩纸均匀的画了 N ∗ M N*M N∗M 个小方格,有些小方格中被他画了小草,以后写小方格是空白的,现小明想找出一片空白的方格,并且这片空白方格是最大的矩形。
给出 N N N 和 M M M 的值,及每个方格的状态,被画小草的小方格用数字 1 1 1 表示,空白小方格用数字 0 0 0 表示,请帮小明找出最大矩形,并输出最大矩形由多少个小方格组成。
例如: N = 4 N=4 N=4, M = 5 M=5 M=5。
【输入】
第一行输入两个正整数 N N N 和 M ( 2 ≤ N ≤ 100 , 2 ≤ M ≤ 100 ) M(2≤N≤100,2≤M≤100) M(2≤N≤100,2≤M≤100),分别表示矩形彩纸方格的行数和列数,两个正整数之间以一个空格隔开
第二行开始,输入 N N N 行,每行 M M M 个正整数(正整数为 1 1 1 或者 0 0 0), 1 1 1 表示小草, 0 0 0 表示空白,正整数之间一个空格隔开
【输出】
输出一个整数,表示最大矩形由多少个小方格组成
【输入样例】
4 5
1 1 0 0 0
1 0 1 0 0
0 0 0 1 1
0 0 0 1 0
【输出样例】
6
【解题思路】
【代码详解】
n, m = [int(i) for i in input().split()]
a = [[0 for i in range(10)] for i in range(10)]
gl = [[0 for i in range(10)] for i in range(10)]
for i in range(1, n+1): # 输入矩形
ls = [int(i) for i in input().split()]
for j in range(1, m+1):
a[i][j] = ls[j-1]
for i in range(1, n+1): # 预处理某行中连续为0的数量
for j in range(1, m+1):
if a[i][j]==0:
if j==1:
gl[i][j]=1
else:
gl[i][j] = gl[i][j-1]+1
ans = 0
for i in range(1, n+1): # 遍历矩形
for j in range(1, m+1):
if a[i][j]==1: # 如果为1直接继续
continue
width = gl[i][j] # 取出width,为gl[i][j]
area = width # 初始化面积为width(即1*width)
for h in range(i, 0, -1): # 高度从i遍历至1(即从下往上找)
width = min(width, gl[h][j]) # 找到最小的宽度
area = max(area, width*(i-h+1)) # 面积就是最小的宽度width * 高度(即i-h+1)
ans = max(ans, area) # 每个单元格都计算一次,计算最大面积
print(ans)
【运行结果】
4 5
1 1 0 0 0
1 0 1 0 0
0 0 0 1 1
0 0 0 1 0
6