Scratch蓝桥杯真题解读系列在推出之后,受到了广大老师和家长的好评,非常感谢各位的认可和厚爱。作为回馈,计划推出《Python蓝桥杯真题解析100讲》,这是解读系列的第36讲。
四位正整数,本题是2020年10月30日举办的第11届蓝桥杯青少组Python编程国赛编程部分第3题,题目要求编写程序将n~m中所有各个位上都是偶数的四位正整数找出来并输出。
先来看看题目的要求吧。
一.题目说明
编程实现:
输入两个不相等的四位正整数N和M,其中N < M,并以逗号分隔,输出N与M之间(包含N和M)所有满足要求的正整数且正整数之间以一个英文逗号隔开。
要求:每个正整数的各个位上的数都为偶数(注:0为偶数)。
输入描述:
输入两个不相等的四位正整数(N,M)
输出描述:
输出N与M之间(包含N和M)所有满足要求的正整数且正整数之间以一个英文逗号隔开
样例输入:
4000,4008
样例输出:
4000,4002,4004,4006,4008
二.思路分析
这是一道涉及枚举算法的题目,考查的知识点主要包括枚举算法、拆位算法、字符串运算等。
根据题目的要求,我们需要对N~M之间所有的整数进行逐一判断,这是典型的枚举算法,直接使用for..in循环即可。这里的重点是如何判断一个4位数各个位上的数是否都为偶数,其核心问题是分别取出每一位数字。
一般来说,有如下两种方法:
- 字符串方式
- 拆位算法
字符串方式的思路就是将数字转成字符串,再通过下标分别取出每一个字符,然后将字符转成数字即可。拆位算法的思路是从低位开始,每一次获取最低位的数字,然后去掉最低位,重复这个过程直到数字变成0。如何获取最低位呢,这是%运算的特长,将数字模10就可以。
如何去掉最低位呢,这是//运算的职责,将数字整除10即可。
我们以数字2347为例来说明这个过程:
# 第1次
获取低位: 2347 % 10 = 7
去掉低位: 2347 // 10 = 234
# 第2次
获取低位: 234 % 10 = 4
去掉低位: 234 // 10 = 23
# 第3次
获取低位: 23 % 10 = 3
去掉低位: 23 // 10 = 2
# 第4次
获取低位: 2 % 10 = 2
去掉低位: 2 // 10 = 0
经过4次运算,我们分别取出了7、4、3、2四个数字,最后数字变成0,拆位结束。为了简化代码,我们可以定义一个函数,用于判断给定数字是否各位数字都是偶数,如果是返回True,否则返回False。思路有了,接下来,我们就进入具体的编程实现环节。
三.编程实现
根据上面的思路分析,我们分两步来编写程序:
- 定义判断函数;
- 枚举判断并输出结果;
1. 定义判断函数
根据前面的思路分析,我们定义函数如下:
代码不难,强调两点:
1). 这里的变量k就是每次获取的最低位,如果k为奇数,则不满足条件,直接返回False,函数结束,如果while循环结束,都没有返回False,说明每一位都是偶数,直接返回True;
2). 在去掉最低位的时候,需要使用整除运算符//,而不是/,二者区别很大。
2. 枚举判断并输出结果
有了上面的iseven()函数,判断就变得非常简单了,但是这里还有两个小问题要解决:
- 如何获取逗号隔开两个整数
- 如何将数字使用逗号连接并输出
对于第一个问题,可以借助字符串的split()方法,其用法如下:
str.split(str="")
参数:分隔符,默认为所有的空字符,包括空格、换行(\n)、制表符(\t)等
返回值:字符串列表
对于第二个问题,则可以使用字符串的join()方法,其用法如下:
str.join(sequence)
参数:要连接的元素序列
返回值:通过指定字符连接序列中元素后生成的新字符串
解决了这两个问题,就可以编写代码了,如下所示:
强调两点:
1). 在获取n和m值时,使用了列表推导式和解包的编程技巧;
2). 为了使用join()方法,我们定义了一个列表,将满足条件的数字保存到列表,需要注意,一定要将数字转成字符串,否则会报错。
关于解包,在之前的教程中也多次提到,这里再说明一下。
在 Python 中,解包是指将容器(如元组、列表、字典等)中的元素分别赋值给多个变量的过程。
举例如下:
# 列表解包
my_list = [1, 2, 3]
x, y, z = my_list
print(x) # 输出: 1
print(y) # 输出: 2
print(z) # 输出: 3
# 元组解包
my_tuple = (4, 5, 6)
a, b, c = my_tuple
print(a) # 输出: 4
print(b) # 输出: 5
print(c) # 输出: 6
输入4000,4008,运行程序,效果如下:
至此,整个程序就全部完成了,你也可以输入不同的数字来测试效果。
四.总结与思考
本题代码在15行左右,涉及到的知识点包括:
- 循环语句,主要for…in循环;
- 输入输出处理;
- 字符串运算;
- 函数的编程思想及使用;
- 拆位算法;
- 枚举算法;
本题难度中等,重点有3个,一是如何获取输入的n和m,二是对整数进行拆位,三是如何将数字用逗号连接起来。
本题中,我们使用了大量和字符串相关的方法(函数),包括split()、str()和join()等,这充分说明,字符串处理是多么的重要,一定要熟练掌握。
在判断四位数是否满足条件的时候,我们专门定义了一个函数,这个是编程中非常重要的模块化思维(结构化思维),从而将一个复杂问题拆分成几个简单问题,务必要多加练习并灵活运用。
最后给你留一道思考题,如果使用字符串方式来判断4位数是否满足条件,代码是如何实现的,和拆位算法相比,二者有哪些区别,哪一个方式更好?