題目
Given a string containing digits from 2-9 inclusive, return all possible letter combinations that the number could represent.
A mapping of digit to letters (just like on the telephone buttons) is given below. Note that 1 does not map to any letters.
Example:
Input: "23"
Output: ["ad", "ae", "af", "bd", "be", "bf", "cd", "ce", "cf"].
思路
題目的本質是多維數組展開爲一維數組,每個數字對應的字符串的長度就是該維的大小,以234
爲例,3個數字對應的字符串長度都爲3,因此三位數組每一維的大小就是3,我們要做的就是把這個3維數組展開爲一維,將一維數組索引轉換爲3維。
一維數組索引 | 三維數組索引 |
---|---|
0 | 0,0,0 |
1 | 0,0,1 |
… | … |
8 | 0,2,2 |
9 | 1,0,0 |
… | … |
26 | 2,2,2 |
代碼
class Solution {
public:
vector<string> letterCombinations(string digits) {
map<char, string> int2str;
buildInt2Str(int2str);
vector<int> multis;
int multi = 1;
for (int i = digits.size() - 2; i >= 0; --i) {
multi *= int2str[digits[i + 1]].size();
multis.insert(multis.begin(), multi);
}
vector<string> res;
for (int i = 0; i < multi * int2str[digits[0]].size(); ++i) {
string s("");
for (int j = 0; j < digits.size() - 1; ++j) {
int idx = i / multis[j];
if (j > 0) {
idx = (i % multis[j - 1]) / multis[j];
}
s += int2str[digits[j]][idx];
}
string last = int2str[digits[digits.size() - 1]];
s += last[i % last.size()];
res.push_back(s);
}
return res;
}
private:
void buildInt2Str(map<char, string> &int2str) {
int2str.insert(pair<char, string>('2', "abc"));
int2str.insert(pair<char, string>('3', "def"));
int2str.insert(pair<char, string>('4', "ghi"));
int2str.insert(pair<char, string>('5', "jkl"));
int2str.insert(pair<char, string>('6', "mno"));
int2str.insert(pair<char, string>('7', "pqrs"));
int2str.insert(pair<char, string>('8', "tuv"));
int2str.insert(pair<char, string>('9', "wxyz"));
}
};
構造數字到字符串的映射表
map<char, string> int2str;
buildInt2Str(int2str);
獲取每一維數組大小
vector<int> multis;
int multi = 1;
for (int i = digits.size() - 2; i >= 0; --i) {
multi *= int2str[digits[i + 1]].size();
multis.insert(multis.begin(), multi);
}
以234數組爲例,第一維大小爲12=3*4,第二維大小爲4,第三維直接取下標
根據一維下標獲取三維數組下標
vector<string> res;
for (int i = 0; i < multi * int2str[digits[0]].size(); ++i) {
string s("");
for (int j = 0; j < digits.size() - 1; ++j) {
int idx = i / multis[j];
if (j > 0) {
idx = (i % multis[j - 1]) / multis[j];
}
s += int2str[digits[j]][idx];
}
string last = int2str[digits[digits.size() - 1]];
s += last[i % last.size()];
res.push_back(s);
}
注意,在獲取第1~(n-1)維的下標時,需要先對前一維的數組大小取餘:
if (j > 0) {
idx = (i % multis[j - 1]) / multis[j];
}