尧图网络 高端网站定制 · 原创设计
免费咨询热线
400-888-6620
免费获取方案
Python编程题161-170深度拆解:从基础语法到综合实战的进阶之路
刷过不少练手题能让我隔一段时间愿意回看的系列不多Python小屋的编程题算一个。最近集中把161-170这十道题从头到尾做了一遍一个明显的感受是题量确实不大但如果想全部一次通过、又快又稳并不比做三十道题轻松。很多题看起来只有三五行代码量真正踩过边界条件和性能坑之后才会明白藏在简单题目背后的编排意图。如果你正处在学完基础语法、想靠做题把知识焊进脑子里的阶段或者你在带学生、需要一套有层次感的练习这套题很适合。它的风格偏基础但绝不放水题目之间还有明显的递进关系比你随手去题库里随机刷题要高效得多。下面我把自己拆题、做题、排错的过程完整摊开来说希望能给你一条可以直接照走的路线。1. 这套编程题适合谁以及它到底在练什么1.1 为什么“会语法”和“会做题”是两回事不少学Python的朋友都有过这种经历循环、列表、字典、函数单讲都能懂看教程里的例子也觉得“好简单”可一关上教程给自己一个空白的.py文件就不知道从哪里下笔。我之前一度把这个问题归结为“不熟练”后来带过几次新人才慢慢理解其实语法知识是碎片化的而做题是一个把碎片组装成完整模型的过程中间缺的不是智商而是大量刻意练习。这套练习题的设计理念恰好踩在这一点上。它不绕弯子题目描述很口语化但要求你必须自己判定边界、自己设计数据结构。第161-170题尤其明显它不再像前面的题那样一题只考一个知识点而是动不动就让你同时处理“字符串清洗 字典计数 排序规则”的组合一层套一层逼你把脑子里那几个孤立的函数连接成完整的解题链路。等你真正把这十道题顺下来再回头写小脚本手感和之前完全不一样。1.2 161-170题处在练习曲线的哪个位置连号题目一般暗示着知识点的重叠这个规律是我刷完对比之后才发现的。前面的题更像在检查“课堂知识点记住了没有”比如判断回文、交换两个数、打印九九乘法表到了中段题目表述开始变长会出现“给定一个列表请统计每个元素出现的次数然后输出”这类需要两三个步骤的组合题而一百六十多题之后题目开始有明显的“数据规模”“输出格式限制”这些工程性要求。所以如果你正好学完Python基础阶段想判断自己能不能进入面向对象、文件处理、算法入门用这一组题自测非常合适。它考的不是某个冷门API而是最常用的几个内置工具加上一点点算法思维比如排序稳定性、字典默认值、递归边界。这些能力是后续学习的底部支撑比单纯记API重要得多。2. 进阶练习题的设计套路六个高频命题方向这十道题我没法在文章里把原题全部复述出来毕竟不同版本可能有调整。但根据我对这个系列编排风格的观察第161-170题几乎都围绕着下面六个方向展开。你把这个拆解吃透做任何一套综合练手题都会有底。2.1 字符串处理看着简单坑最多字符串题目看起来最“友好”不给数据结构、不给对象只给一段文本。可它恰恰是翻车率最高的地方。常见命题形式有三种统计一段文本中字母出现的频次忽略大小写和标点按规则过滤非法字符比如只保留汉字或数字从原始文本中提取一串日期、手机号、编号并格式化输出。做这类题有一个原则先统一数据源再做分析。我见过太多次因为直接使用大小写混合的原始字符串导致统计结果对不上的情况。常规做法是先归一化用lower()把文本统一成小写再用正则把有效字符筛出来最后才计数。如果没有正则基础用字符串方法配合列表推导也能实现但代码可读性会差不少。另外字符串题里的空串和全符号字符串是高频边界陷阱。输入只有一个空格、输入是空文件这些情况都要在写代码之前先想好不要等到评测反馈了再回去补。2.2 容器组合列表、字典、集合的嵌套操作这一组题目里最热闹的方向是把两个或三个内置容器叠加起来出题。典型场景是输入几行记录每行包含编号、类别、数值要求按类别分组输出每组的总和、均值、最大值。这类题在初学阶段第一版答案几乎都是“三层for循环加上if挨个比”。小数据能跑对数据一大就变得很慢。更好的做法是先想清楚“以谁为key、以什么为value”需要按类别分组key一定是类别value则可以是一个包含总人数和总值的列表。代码结构从“先找所有类别再逐类统计”变成“边读边累加”复杂度也从两层循环降成一趟遍历。一个实用技巧是优先使用字典的setdefault方法或collections.defaultdict能省掉大量“这个key是否存在”的判断。161-170这个段位经常出现“你知不知道defaultdict”这类隐含考察点用上了不仅代码简练而且不容易出错。2.3 递归与分治弱化循环强调模型这个区间里几乎必有递归题但它很少直接让你写“计算阶乘”这种入门示例而是把递归包装在现实场景里比如计算某种排列组合的数量、模拟爬楼梯或硬币组合或者处理“列表里的列表”这种嵌套结构。做递归题的要点有两个。第一把递归出口写在函数最前面第二千万不要在脑子里强行模拟递归的每一步执行新手根本模拟不过来。正确方式是先用数学公式写出递推关系比如f(n)f(n-1)f(n-2)再翻译成代码。如果你写递归时总头晕可以先练习用“自底向上”的循环版本写出同样结果再回头看递归写法理解通常会快很多。还要提一个必踩的坑性能。朴素递归往往导致指数级重复计算在练习系统里表现为“数据一大就超时”。解决办法有两个一是手动记录中间结果就是记忆化二是用Python的functools.lru_cache装饰器一行代码就能显著提速。这类题的目的不是考递归语法而是考你有没有把递归看成“有状态的动态规划雏形”。2.4 类与对象从“工具函数”到“状态管理”练习进入一百多题之后命题人会开始试探你对类的掌握。常见形式是让你设计一个很小的类比如计数器、任务队列或一个带简单规则的状态机然后通过若干调用验证其内部状态。很多人第一次写类会本能地把所有状态放在全局变量里函数里改完就算过去了。这样也能混过一部分用例但一旦要求创建多个实例、互不影响全局变量方案立刻露馅。正确思维是把需要长期保存的数据放到实例属性中让方法只通过self读写属性外部通过方法调用而不是直接改属性。另外写类时要注意规范初始化的命名。__init__里定义了哪些属性就保持哪些属性不要中途突然新增否则很容易出现因为拼写不一致导致“赋值了但还是没值”的诡异问题。这类题的目的是让你从“写脚本”过渡到“定义可复用的结构”这也是后面做小项目时的核心技能。2.5 文本与数据清洗贴近真实开发场景这组题里还有一类“看起来代码量最大”的题给一个多行文本或者一个模拟文件里面有大量空格、空行、特殊字符要求按规则提取信息再输出成整齐的表格或指定格式。这类题其实就是mini版数据清洗是真实开发中数据处理最常见的雏形。处理这类题我记住一个“分阶段管线”的口诀读入、清洗、转换、输出四个阶段尽量不要混着写。很多初学者会在同一个列表推导式里一边清理一边计数一边格式化最后代码一团糟还容易重复造轮子。把每一步拆成清晰的小函数写的时候看着慢调试起来快十倍。正则清洗是最安全的方案应该尽早纳入技能包。哪怕只是最常用的re.findall配合字符类也能解决大部分非法字符和空白字符问题。如果练习环境不允许导入re退而求其次用字符串的isalnum、isalpha等方法逐个字符判断也能凑合实现只是性能略差。2.6 边界条件和基础算法评测系统真正想考察的最后这一类不是单独一道题而是命题人铺在所有题里的“暗线”。很多题表面在考字符串实际在考你对边界的敏感度表面在考排序实际在考察你是否了解排序函数在相等情况下的稳定性。举个例子要求“按次数降序次数相同按字典序升序”时如果只会调用一个sort没有搞懂key传一个元组时的排序规则写错顺序的概率非常高。再看空列表、只有一个元素、全部元素都相同、负数输入这些场景任何有经验的出题老师都会埋在用例里。应对方式其实很简单读题之后先不急着写花几十秒在草稿纸上写出三五个极端输入然后想想自己的算法在这些输入上会发生什么。坚持这样做准确率会有明显提升。3. 手把手过一道题完整的解题流水线下面用一个很有代表性的题型——词频统计并排序——来演示完整解题过程。它综合了字符串清洗、字典计数、排序规则三项能力难度和161-170段位很接近。3.1 第一步不要动手先把题目翻译成人话题目大致是输入一段英文文本可能包含大小写字母、数字、空格和英文标点要求忽略大小写和标点统计每个单词出现的次数先按次数降序如果次数相同则按单词字典序升序最后把每个单词和次数放在一行输出单词和次数之间用英文冒号分隔。我第一次见这道题时差点直接写上split( )。稍一琢磨就发现不行文本里有逗号、句号、感叹号简单按空格切分会把“Hello,”当成一个带逗号的词统计结果完全不对。随后我在草稿上写下两行拆解规范化把大写转小写把非字母字符从单词中剔除分组计数以规范化后的单词为key累加出现次数。这基本上就是题目的全部核心。翻译成人话之后一切都会变得非常可控。3.2 第二步构造三个用例把“弱问题”逼出来我习惯构造三类测试数据目的不是验证代码能跑而是验证边界。第一个是最简单的无标点样例text1 hello world hello期望输出里hello出现2次world出现1次hello次数更高排在前面。第二个是带标点和大写的样例text2 Hello, world! Hello Python. Python, python.期望输出里hello出现2次python出现3次world出现1次标点不能混进单词尾部。第三个是空文本text3 期望输出为空而不是报错。想清楚这些才动手写代码后面会省掉很多返工。3.3 第三步编码时保持“一次成型”的纪律我的完整代码如下import re from collections import Counter def top_word_freq(text: str): words re.findall(r[A-Za-z], text.lower()) counter Counter(words) # 次数降序单词升序利用key元组实现 return sorted(counter.items(), keylambda item: (-item[1], item[0])) text Hello, world! Hello Python. Python, python. for word, cnt in top_word_freq(text): print(f{word}: {cnt})这段代码里最关键的三个决策使用re.findall而不是split。正则r[A-Za-z]会把一串连续字母当成一个整体取出来自动跳过空格和标点。这是让代码简短又正确的核心一步。统一调用lower()之后再做findall。正则结果里的字符全部是小写后续统计不会出现“Python”和“python”被算成两个词的问题。排序时key写成(-item[1], item[0])。次数前加负号是降序单词默认升序Python的sort会先比较第一个元素相等再比较第二个元素所以这两条规则被一个元组完整表达。运行结果如下python: 3 hello: 2 world: 1只要语法正确这段代码一次就能通过大部分评测。不过我还会多走一步验证。3.4 第四步测试、边界、性能检查把空文本丢进去试了一下re.findall返回空列表Counter是空的sorted结果也是空的for循环不执行不会报错符合预期。接着生成一个一万词的文本再测一次Counter内部用哈希表统计复杂度是O(n)排序是O(k log k)整体在大文本下表现很稳定不会出现几百毫秒跑不完的情况。到这里一个词频统计题才算完整过完。很多人只做到“代码通过了”就收工我不建议这样。多花五分钟把极端用例和复杂度分析做了下一次遇到数据规模变大时才不会措手不及。4. 再拆两道高频类型题分组统计与去重排序为了让第2章的“命题方向”落到具体代码上我再拆两道很典型的题型它们都是161-170这个段位常见的外壳。4.1 按班级统计平均成绩并排序输出题目场景可以抽象为给出若干行记录每行是“班级名,学生名,分数”要求计算每个班级的平均分按平均分从高到低输出如果平均分相同则按班级名字典序升序输出。这类题大多数人都能写出来但代码质量差异很大。最差的写法是“先把班级放进一个列表再循环每个班级去原数据里统计”小数据勉强能跑数据量一上来就是O(n*m)需要优化。更好的写法是只遍历一遍数据边累加边计数from collections import defaultdict def class_average(records): # key 为班级value 为 [总分, 人数] agg defaultdict(lambda: [0, 0]) for cls, _, score in records: agg[cls][0] score agg[cls][1] 1 result [(cls, total / cnt) for cls, (total, cnt) in agg.items()] result.sort(keylambda item: (-item[1], item[0])) for cls, avg in result: print(f{cls}: {avg:.2f})defaultdict(lambda: [0, 0])的意思是班级第一次出现也能直接累加省掉“if cls not in agg”的判断同时不会引入KeyError。排序规则仍然靠负号加元组完成和词频题的写法保持一致。如果评测要求返回列表而不是打印只要把result返回出去就行。4.2 超大文本中的Top N词频统计这类题在原系列里也有类似变体进阶点在于对时间和空间有要求。比如输入一篇文章要求输出出现次数最多的前10个单词。如果只用列表的count方法每查一个词就要遍历整个列表复杂度是O(n^2)几千词的时候就会卡到让人崩溃。正确做法和前面的词频题一致用Counter统计全部词频再用most_common(N)取出前N项。Counter底层是哈希表统计接近O(n)排序只在取前N时发生复杂度合理。from collections import Counter import re def top_n_words(text: str, n: int 10): words re.findall(r[A-Za-z], text.lower()) return Counter(words).most_common(n)有一个细节必须提醒most_common返回的顺序是“次数降序”但如果出现次数相同它内部不保证字典序。如果题目要求同频按字典序需要改成counter Counter(words) sorted(counter.items(), keylambda item: (-item[1], item[0]))[:n]这个差异很容易被忽略而评测系统恰恰最喜欢在这种地方出“阴间用例”。5. 刷题中的常见报错与排查技巧实录做161-170这类综合题时遇到的报错很多时候不像基础题那么直接。我挑几个高频问题结合自己排查的经验讲一讲。5.1 本地结果没问题提交却判错这是练习系统里最打击人的情况十有八九是输出格式问题多打印了一个空格、最后一行多了换行、或者把提示信息也print了出来。以词频统计题为例要求“单词:次数”中间是英文冒号如果用中文冒号或者在冒号后面多写一个空格本地永远看不出来评测一挂一个准。我的排查经验是“把输出黑盒化”只看程序产生的完整输入输出不靠肉眼猜。在本地可以用repr把结果包起来打印比如print(repr(result_str))末尾空格和不可见字符立刻显形。做在线判题类练习时能不用手写空格美化就不用尽量用join或f-string让代码自己控制格式。5.2 死循环、无限递归与“没有任何反应”综合题里出现死循环最可能出问题的位置是while循环的退出条件。常见错误是更新条件放错了位置或者退出条件判断的是“未来才会变化的量”。排查时我会在循环体第一行加print调试变量观察它是否按预期变化。如果连续输出十次都一样说明状态没有更新直接修正退出条件。无限递归更好判断报错信息里会出现RecursionError。出现它不一定代表递归层数真的特别深而可能只是递归出口在某种输入下永远到不了。对照前面的经验第一件事检查递归函数第一行是不是出口判断第二件事检查递归调用传入的参数是否在向出口方向逼近。比如计算斐波那契时调用f(n-1)、f(n-2)两个参数都比n小方向是对的如果写成f(n1)那只能等着爆栈。5.3 数据一多就变慢复杂度改进实例第161-170题里有些题看起来简单实际数据规模很大评测系统会在时间上卡得很死。常见现象是“样例输出正确提交后超时”。碰到这种情况优先检查自己是不是在循环里调用了count、index、in列表这类O(n)操作。举个例子如果用“每个元素删掉后重新拼接列表”的方式处理长列表每次拼接都是O(n)整体可能到O(n^2)改成在新列表里跳过需要删除的元素一次遍历搞定就是O(n)。宁可多花五分钟想数据结构也不要靠暴力循环硬扛。5.4 一套自检清单我会把自己做题时养成的检查习惯整理成清单方便你直接对照检查输入是否可能为空字符串、空列表、None检查是否有大小写、前后空格需要统一检查索引是否有越界风险尤其涉及range(len(...)-1)时检查排序规则降序是否加了负号、同键时是否明确二级排序检查字典赋值前是否处理了“key不存在”的情况检查循环退出条件是否在每次迭代都会向终止方向收敛检查输出格式是否和题目严格一致。对照这份清单任何一题都能少跑一遍冤枉路。6. 把练习变成长期资产的一个习惯刷完这十道题我最大的收获不是多会了几种解法而是对“出题人到底想考什么”变得敏感了。以后每次看到新的练习题我会先读两遍题目把“输入是什么、输出是什么、哪一步最容易出错”写在注释里再开始写代码。这个习惯帮我省掉了大量返工。另一个值得分享的小做法是每做完一题我会顺手在文件顶部写三行注释分别记录“考点”“我的解法”“更快或更简单的解法”。过一周再回来看看到“考点”那一行先回忆解题思路看到“更快或更简单的解法”已经想不起来了说明这块知识需要重温。这样一套几十题的记录慢慢就成了完全对口的复习资料比收藏任何别人整理好的题解都管用。如果你也正处在啃Python练习题的中间阶段不妨先不看数量静下心把这类综合题彻底吃透。真正让你发生质变的不是又多刷了十道而是你终于开始用“解题系统”的眼光去看每一道题。
RELATED

相关推荐

条件卷积如何提升实例分割精度与效率

条件卷积如何提升实例分割精度与效率

/* MD / 富文本中的 .toc(含博客园搬家等嵌套结构);.toc-box 在侧栏,不受影响 */#content_views .toc,/* 编辑器常在目录前后插入空 p(:empty 仍占 20px),一并去掉避免顶空隙 */#content_views.markdown_views > p:empty:has(+ .toc),#content_views.markdown_views …

📅 2026/10/15 1:32:41
ROS导航栈仿真实战:定位move_base失效的五大隐性断点

ROS导航栈仿真实战:定位move_base失效的五大隐性断点

/* MD / 富文本中的 .toc(含博客园搬家等嵌套结构);.toc-box 在侧栏,不受影响 */#content_views .toc,/* 编辑器常在目录前后插入空 p(:empty 仍占 20px),一并去掉避免顶空隙 */#content_views.markdown_views > p:empty:has(+ .toc),#content_views.markdown_views …

📅 2026/10/15 1:32:41
STC15万年历设计与DS1302驱动全解析:从硬件接线到避坑指南

STC15万年历设计与DS1302驱动全解析:从硬件接线到避坑指南

/* MD / 富文本中的 .toc(含博客园搬家等嵌套结构);.toc-box 在侧栏,不受影响 */#content_views .toc,/* 编辑器常在目录前后插入空 p(:empty 仍占 20px),一并去掉避免顶空隙 */#content_views.markdown_views > p:empty:has(+ .toc),#content_views.markdown_views …

📅 2026/10/15 1:27:41
MORE NEWS

更多资讯

📰

M3U8 文件 BOM 头部标记,看不见字符带来解析失败

、看不见的 BOM 头部带来解析失败 很多新手遇到一类诡异故障:M3U8 内容肉眼看完全没问题,第一行写的就是 #EXTM3U,VLC 播放器播放一切正常,但是浏览器 hls.js 直接解析报错,播放黑屏。 根源就是 UTF‑8 BOM 标记。BO…

📰

随身WiFi突然断网限速?八成是卡被风控了:停机原因自查清单

前排提醒:本文只讨论随身WiFi与流量卡的使用排查研究,素材来自公开资料整理,不构成任何渠道推荐。最迷惑的一种故障:设备灯正常、信号满格、余额也在,就是上不了网。折腾半天设备,最后发现是卡被风控停机了…

📰

Java基础:为什么两个String明明一样,使用==比较却是false?深入理解==和equals()区别

在学习 Java 的过程中, 和 equals() 几乎是每个初学者都会遇到的一个问题。很多刚开始学习 Java 的同学都会记住一句话:String 比较不要使用 ,应该使用 equals()但是为什么?为什么下面这段代码中,两个 String 明明都是…

📰

随身WiFi一到晚高峰就卡?先看懂QCI优先级,别急着怪设备

前排提醒:本文只讨论随身WiFi设备与流量卡的技术原理与使用研究,数据来自公开资料整理,不涉及任何具体渠道推荐。一个高频吐槽:白天测速满血,一到晚高峰就缩水;换台设备、换个卡槽,还是卡。不少…

📰

aigc检测报告怎么看?2026年论文AI率免费检测和付费检测攻略,超标先降AI!

论文写完了,查重率也降下来了,学校又要求提交AIGC检测报告。搜索一下,免费查AI率的网站、知网检测入口、降AI率软件混在一起:到底应该用哪个? 是不是每修改一次论文,都要重新花钱查AI率? 可以…

📰

Flashlight Emoji 插件深度解析:从 `emoji grin` 到 `:rocket:` 的搜索与复制机制

桌面应用插件系统 【免费下载链接】Flashlight The missing Spotlight plugin system 项目地址: https://gitcode.com/gh_mirrors/fl/Flashlight 点击查看 免费下载 导读 本文围绕 Flashlight(macOS Spotlight 插件系统)官方插件目录中的 E…

TODAY

今日更新

THIS WEEK

本周精选

THIS MONTH

本月热门

读完文章,想聊聊您的网站?

告诉我们您的行业与需求,资深顾问一对一梳理方案与报价,全程免费。

📞 💬