题目
给定一个仅包含数字 2-9
的字符串,返回所有它能表示的字母组合。给出数字到字母的映射如下(与电话按键相同)。注意 1 不对应任何字母。
输入:"23" 输出:["ad", "ae", "af", "bd", "be", "bf", "cd", "ce", "cf"].
分析
本题目实质依旧是组合问题,但是与之前两道组合 77题组合、216题组合总和||| 有些不同,它是由多个集合来求解组合。脑中构建搜索树形状:for循环水平搜索每个集合元素,递归纵向搜索,深度就是集合的个数,如23就就是数字2对应字母的集合、数字3对应字母的集合,所以深度就是2。注意:因为每个集合所包含元素的个数不等,故应该在for循环 前确定元素个数(代码22—23行)
纵向搜索多个集合
代码
1 class Solution { 2 public: 3 string path; 4 vector<string>res; 5 const string letterMap[10] = { 6 "",//0 7 "",//1 8 "abc",//2 9 "def",//3 10 "ghi",//4 11 "jkl",//5 12 "mno",//6 13 "pqrs",//7 14 "tuv",//8 15 "wxyz",//9 16 }; 17 void backtracking(string digits,int index){ 18 if(path.size() == digits.length()){ //或者index == digits.size() 19 res.push_back(path); 20 return; 21 } 22 int digit = digits[index] - '0';//将每个字符转换为整型好做哈希 23 string letters = letterMap[digit];//取出对应数字的字符串 24 for(int i = 0;i < letters.length();i++){ 25 path.push_back(letters[i]); 26 backtracking(digits,index + 1); 27 path.pop_back(); 28 } 29 } 30 vector<string> letterCombinations(string digits) { 31 if(digits.length() == 0) return res; 32 backtracking(digits,0); 33 return res; 34 } 35 };
总结:
1.多集合的组合问题中index与单集合的组合问题中的index含义不一样,前者表示是从第几个集合取数,也就是目前到达的递归深度。而后者表示单个集合的取数位置。
2.数字和多个字母如何做映射?其本质思想来源于哈希,用字符串数组做哈希,数组下标索引代表数字,与之对应的每个字母组合成字符串存于该位置。