电话号码的字母组合(DFS+回溯法)
发布日期:2021-05-04 06:33:47 浏览次数:51 分类:精选文章

本文共 1465 字,大约阅读时间需要 4 分钟。

递归三部曲:深入理解递归思维

递归作为一种强大的算法思维方式,常用于解决复杂问题。本文将通过一个经典的组合问题,带你深入理解递归的三部曲。

问题背景

我们需要解决的问题是:给定一串数字,每个数字对应一个字母序列,找出所有可能的字母组合。例如,数字"23"可以组合成"ad"、"ae"、"bd"、"be"等。

思路概述

这个问题可以通过回溯法(Depth-First Search, DFS)来解决。回溯法是一种递归解法,适合用于生成所有可能的组合或排列。递归的三部曲可以帮助我们清晰地理解整个过程。

递归三部曲

第一步:确定递归结束的条件

递归结束的条件是当输入的数字序列为空时,表示所有可能的组合已经生成。具体代码如下:

if (numberstr.size() == 0) {    res.push_back(cur);    return;}

第二步:理解每个递归返回值

每个递归调用都会处理当前数字对应的字母序列,然后递归处理剩下的数字序列。最终,递归返回时会将生成的组合添加到结果中。

第三步:明确本级递归的任务

在当前数字对应的字母序列中,依次处理每个字母,将其压入栈底,然后调用递归处理剩下的数字序列,最后弹出字母。代码如下:

string letterstr = mp[numberstr[0]];for (int i = 0; i < letterstr.size(); i++) {    cur.push_back(letterstr[i]);    DFS(numberstr.substr(1));    cur.pop_back();}

代码实现

#include 
#include
#include
#include
#include
using namespace std;map
mp = { {'2', "abc"}, {'3', "def"}, {'4', "ghi"}, {'5', "jkl"}, {'6', "mno"}, {'7', "pqrs"}, {'8', "tuv"}, {'9', "wxyz"}};class Solution {private: vector
res; string cur;public: vector
letterCombinations(string numberstr) { if (numberstr.size() == 0) return res; DFS(numberstr); return res; } void DFS(string numberstr) { if (numberstr.size() == 0) { res.push_back(cur); return; } string letterstr = mp[numberstr[0]]; for (int i = 0; i < letterstr.size(); i++) { cur.push_back(letterstr[i]); DFS(numberstr.substr(1)); cur.pop_back(); } }};

总结

通过递归三部曲,我们清晰地理解了回溯法的工作原理。每个递归调用处理当前数字对应的字母,然后递归处理剩下的数字,最终生成所有可能的组合。这种方法高效且简洁,适用于类似的问题。

上一篇:图的遍历(典型的DFS)
下一篇:effective_考虑写出一个不抛出异常的swap函数(涉及到pimpl手法)

发表评论

最新留言

第一次来,支持一个
[***.219.124.196]2025年05月01日 00时26分48秒