LeetCode--電話號碼的字母組合
阿新 • • 發佈:2019-01-26
給定一個僅包含數字 2-9 的字串,返回所有它能表示的字母組合。
給出數字到字母的對映如下(與電話按鍵相同)。注意 1 不對應任何字母。
輸入:"23"輸出:["ad", "ae", "af", "bd", "be", "bf", "cd", "ce", "cf"].
最初拿到這個題的時候我想的是通過迴圈來解決,如果通過迴圈的話,會有很多的問題,或者可以通過迴圈來模擬回溯法也是可以實現的。先說一下我的思想,最初我想的是,在開闢好的空間裡直接放入資料,比如題目中給出的示例是23,我在放的時候,先把2中的a放三個,再把2中的b放三個,再把c放三個,但是這樣就出現了問題,那到3的時候怎麼放,如果和上邊一樣的話就會出現ad ad ad be be be cf cf cf這種情況,因為這是一個迴圈來解決的,所以存放的方式不能夠區別對待,也就是前一個怎麼放後一個還是怎麼放,所以就出現了我上邊的問題。
這種問題無非就是兩種方式迴圈解決不掉了,那就用遞迴
class Solution { public: vector<string> letterCombinations(string digits) { vector<string> str; if (digits.size() == 0) { return str; } string s; Combinations(digits, s, 0, str); return str; } private: void Combinations(string& digits, string& s, int index, vector<string>& str) { if (index == digits.size()) { str.push_back(s); return; } int num = digits[index] - '0'; string letter[10] = { " ", " ", "abc", "def", "ghi", "jkl", "mno", "pqrs", "tuv", "wxyz" }; for (int i = 0; i < letter[num].size(); i++) { s.push_back(letter[num][i]); Combinations(digits, s, index + 1, str); s.pop_back(); } return; } };
不過自己對回溯法加遞迴的問題理解的並不是很透徹。不知道什麼時候要用這個,這裡不如就一點一點分析一下整個程式是怎麼走的。我們就拿題目示例給的23來演示一下。
先說一下函式裡的引數,分別是題目給的23字串,以及我們排列組合之後要插入的字串s,以及index,index是用來記錄我們遞迴層數的,也就是題目給我們的digits的長度是多少就遞迴幾層,index等於digits的說明不能往下迴圈了。第四個引數就是我們的要返回的vector,注意一定要傳引用的形式。
Combinations(digits, s, 0, str);
最初的時候傳入的引數都是空和0,之後進入函式開始遞迴。
int num = digits[index] - '0'; string letter[10] = { " ", " ", "abc", "def", "ghi", "jkl", "mno", "pqrs", "tuv", "wxyz" }; for (int i = 0; i < letter[num].size(); i++) { s.push_back(letter[num][i]); Combinations(digits, s, index + 1, str); s.pop_back(); }
我們先獲取出來當前digits的對應位置的數字是多少,然後通過這個數字去我們letter數組裡邊的下標來找到他對應的字母組合。
找到之後開始把這些字母分別插入到s字串裡邊。第一次迴圈的時候我們插入了a,然後這是再去呼叫我們的Combination函式,這時候和第一次呼叫的時候有所不同,這時候引數裡邊s已經不是空的了,而是包含一個a,index+1變成了1,str還是沒變。當進去之後,我們再次通過num獲取digits下標為1的位置的數字,然後還是找到對應的字母組合,開始遍歷,之後我們在字串s中插入了d,然後又進入了迴圈,s內容是ad,index變成了2這時候。
if (index == digits.size())
{
str.push_back(s);
return;
}