题目描述
思路解析动画文字版
把两个字符串排序再比较是常见做法。小写字母只有 26 种,用计数更贴题。
同一个字母在 s 里出现一次就加一,在 t 里出现一次就减一。完全抵消就是异位词。
长度先判:长度不同直接 false。长度相同才有机会全部抵消。
a 与 n:同一步里:s 的 a 加一格、t 的 n 减一格,是一升一降同时发生。账本开始变化。
n 与 a 抵消:下一对是 n 和 a,刚好把前面的账抵消掉。
继续逐位抵消:走到 g 这一对,g 和前面 s 里多出来的 g 名额抵平,账面又全归零。每个位置都做一次加一减一,不关心顺序,只关心总次数。
全部归零:最后 26 个计数都回到 0,说明两个词字母账完全一样。
反例 · rat vs car 抵不平:s=rat 给 r a t 各加一,t=car 给 c a r 各减一。r 和 a 抵平归零,但 s 多出的 t 和 t 串多出的 c 配不上对,账没清零,返回 false。
顺序不重要,次数完全相同才重要。
边界三连:空串、长度不同、重复字符,是这题最该先过的三类边界。
雷区实演 · set 会误判:aab 和 ab 的字符集合都是 {a,b},但 a 的次数不同,不能只比 set。
面试追问 1:题目限定小写才用 26 槽;真出现 Unicode 就退回哈希表,思路一样、容器换掉。
面试追问 2:计数是 O(n) 更快;排序胜在不挑字符集、代码短,临场记不清索引时可保命。
面试追问 3:set 只记“有没有”,不记“几个”——异位词恰恰要比的就是次数。
这题学完不要乱跳,下一步去 对应专题 连刷同类题;卡住时用 AI 答疑追问“为什么这一步成立”,比只背答案更稳。
参考代码
class Solution: def isAnagram(self, s, t): if len(s) != len(t): return False cnt = [0] * 26 for a, b in zip(s, t): cnt[ord(a) - ord('a')] += 1 cnt[ord(b) - ord('a')] -= 1 return all(x == 0 for x in cnt)复杂度
- 时间复杂度:O(n),两个字符串各扫一遍
- 空间复杂度:O(1),只用 26 个计数槽
可套用的代码模板
这不是复读参考答案,而是把本题“两串计数对冲”抽成可背骨架:换题只需替换三处——字符域大小、索引(x) 怎么算、以及“全 0 才相等”这条收尾判断。如 LC383 赎金信就把“减不到负”改成“B 多出来就 false”。
# 计数对冲:A 串加、B 串减,最后看账本是否全 0if len(A) != len(B): return False # 先卡长度cnt = [0] * 字符域大小 # 小写字母=26for x, y in zip(A, B): cnt[索引(x)] += 1 # A 出现:加 cnt[索引(y)] -= 1 # B 出现:减return all(v == 0 for v in cnt) # 全抵消才相等易错点
面试追问把动画讲成自己的话
追问如果包含 Unicode 怎么办?
这道题到这就讲完了。动画和文字是同一套思路——别光看,关掉页面自己默写一遍。然后顺着主线继续:
两数之和
LeetCode 1 · 简单 · 沿着 数组 & 哈希 继续往下推进
把这道题真正学会,再走
图解算法年卡 ¥99 /年
- ✓本题每步动画的吴师兄语音讲解(全站陆续覆盖)
- ✓小欧带 8 步通关训练——追问到不看答案也能写对、能 30 秒讲给面试官听
- ✓学习报告,记录每道题的掌握程度
76k+ GitHub Star · 吴师兄开源图解算法,几十万开发者在看的算法讲解
想成体系刷透这类套路?去图解算法专题