当前位置: 首页 > news >正文

Leetcode-100 回溯法-电话号码的字母组合

电话号码的字母组合

题目描述

给定一个仅包含数字 2-9 的字符串,返回所有它能表示的 字母组合。答案可以按 任意顺序 返回。

给出的数字到字母的映射如下(与电话按键相同):

2 -> "abc"  
3 -> "def"  
4 -> "ghi"  
5 -> "jkl"  
6 -> "mno"  
7 -> "pqrs"  
8 -> "tuv"  
9 -> "wxyz"

示例 1:

输入: digits = "23"
输出: ["ad", "ae", "af", "bd", "be", "bf", "cd", "ce", "cf"]

示例 2:

输入: digits = ""
输出: []

示例 3:

输入: digits = "2"
输出: ["a", "b", "c"]

解题思路

本题可以使用 回溯法(Backtracking) 来解决。

  1. 定义映射关系:使用 Map 数组存储 2-9 每个数字对应的字母。
  2. 回溯搜索:递归构造字符串,每次从当前数字的字母集中选择一个,并递归处理下一个数字。
  3. 终止条件:当路径长度等于输入数字长度时,将其加入 ans

代码实现

from typing import List

class Solution:
    def letterCombinations(self, digits: str) -> List[str]:
        Map = ["", "", "abc", "def", "ghi", "jkl", "mno", "pqrs", "tuv", "wxyz"]       
        n = len(digits)

        if not n:
            return []

        path = []
        ans = []

        def backtrack(n):
            if n == len(digits):
                ans.append(''.join(path.copy()))
                return

            for i in range(0, len(Map[int(digits[n])])):
                path.append(Map[int(digits[n])][i])
                backtrack(n+1)
                path.pop()

        backtrack(0)
        return ans

时空复杂度分析

时间复杂度

  • 每个数字最多对应 4 个字母,如果 digits 长度为 n,则组合数最多为 4^n
  • 时间复杂度:O(4^n)

空间复杂度

  • 递归调用栈 最多深度为 n,回溯过程中 path 存储当前路径,额外 O(n) 空间。
  • 结果列表 ans 可能存储 4^n 个字符串。
  • 总空间复杂度:O(n + 4^n)

回溯流程示例

digits = "23" 为例,回溯过程如下:

起始状态:[]

选择 'a' → [a]  选择 'd' → [ad]  → 终止,加入结果
                    回溯:移除 'd' → [a]
                    选择 'e' → [ae]  → 终止,加入结果
                    回溯:移除 'e' → [a]
                    选择 'f' → [af]  → 终止,加入结果
                    回溯:移除 'f' → []

选择 'b' → [b]  选择 'd' → [bd]  → 终止,加入结果
                    ...
                    选择 'f' → [bf]  → 终止,加入结果

选择 'c' → [c]  选择 'd' → [cd]  → 终止,加入结果
                    ...
                    选择 'f' → [cf]  → 终止,加入结果

最终输出:["ad", "ae", "af", "bd", "be", "bf", "cd", "ce", "cf"]


易错点解析

为什么循环起点是0 而不像之前的题目为 n

如果起点为n,那么在遍历下一个字符串时,位置为0的字符串首位将永远遍历不到。

回溯函数参数为何传递 n+1 而不是 i+1

  • 这里 n 代表当前处理的数字位置,而不是选取的字母索引。
  • 递归进入下一层时,我们希望处理的是 digits[n+1] 对应的字母,而不是当前 digits[n] 的下一个字母。
  • 如果传递 i+1,则逻辑变为跳过部分字母,导致组合不完整。

为什么 path.copy() 必须在 ans.append() 中使用?

  • path 是一个可变列表,如果直接 append(path),在后续递归回溯修改 path 时,会影响 ans 中已经存储的内容。
  • path.copy() 生成一个新的列表,避免后续修改对 ans 产生影响。

相关文章:

  • 初识Qt(一)
  • 经销商订货管理系统小程序PHP+uniapp
  • beamforming
  • 免费使用!OpenAI 全量开放 GPT-4o 图像生成能力!
  • java基础知识和语法
  • S32K144外设实验(六):FTM输出单路PWM
  • JVM 如何打破双亲委派模型?
  • Arduino硬件控制开发基础资料
  • 消息队列Message Queue
  • Baklib内容中台的核心定位是什么?
  • 创新驱动 智领未来丨中威电子全景展示高速公路数字化创新成果
  • rent8_wechat-新增提醒收租功能
  • 青少年编程与数学 02-013 初中数学知识点 03课题、数与代数
  • 【LVS】负载均衡群集部署(DR模式)
  • VLAN 高级特性
  • STM32F103_LL库+寄存器学习笔记11 - 串口收发的中断优先级梳理
  • 菜鸡前端计算机强基计划之CS50 第七课 python 入门—— Python 中文件操作专题学习
  • ExpTimerApcRoutine函数分析之作用是ActiveTimerListHead里面移除定时器_etimer
  • dockerfile构建镜像方式
  • 前端解决方案:实现网页截图并导出PDF功能
  • 媒体:中国女排前队长朱婷妹妹被保送浙大受质疑,多方回应
  • 人民日报民生观:转人工客服,怎么这么难?
  • 沪喀同心|为新疆青少年提供科普大餐,“小小博物家(喀什版)”启动
  • 王毅谈中拉论坛第四届部长级会议重要共识
  • 75万买299元路由器后续:重庆市纪委、财政局、教委联合调查
  • 王毅会见巴西外长维埃拉、总统首席特别顾问阿莫林