一、 題目
給定一個字符串包含26個字母,字母與數字產生映射,如:
‘A’ --> 1
‘B’ --> 2
…
‘Z’ --> 26
如果給一串數字,請給出編碼的方式有多少?
*注意:’12’ 可以編碼成”AB”,也可以編碼成”L”.
二、 分析
可以看出題目的目的是考察動態規劃,即每走一步可能有兩種情況,是不是和爬臺階很像呢?對的。
這道題思路有兩種但是思路是一樣的:
1、 從前往後遍歷
(1)、ans[0] = 1;
(2)、如果s[0] = ‘0’,ans[1] = 0;否則ans[1] = 1;
(3)、遍歷判斷s[i-1]是否等於’0’,爲0則ans[i] = 0;否則等於ans[i-1],再判斷與後面一位組成的數是否大於26,小於則ans[i]= ans[i] + ans[i-2]
2、 從後往前遍歷
(1)、ans[len] = 1;
(2)、如果s[len-1] = ‘0’,ans[len-1] = 0;否則ans[len-1]= 1;
(3)、遍歷判斷s[i]是否等於’0’,爲0則continue;否則判斷與後面一位組成的數是否大於26,大於則ans[i] = ans[i+1],否則ans[i] = ans[i+1] + ans[i+2]
1、正序遍歷法:
class Solution {
public:
int numDecodings(string s) {
int len = s.size();
if(len == 0) return 0;
int ans[len+1];
ans[0] =1;
if(s[0] != '0')
ans[1] = 1;
else ans[1] = 0;
for(int i=2;i<=len;i++){
if(s[i-1] != '0')
ans[i] = ans[i-1];
else ans[i] = 0;
if(s[i-2] == '1'||(s[i-2] == '2' && s[i-1] <= '6'))
ans[i] = ans[i] + ans[i-2];
}
return ans[len];
}
};
class Solution {
public:
int numDecodings(string s) {
int len = s.size();
if(len == 0) return 0;
int ans[len+1];
memset(ans,0,len*sizeof(int));
ans[len] =1;
if(s[len-1] != '0')
ans[len-1] = 1;
else ans[len-1] = 0;
for(int i=len-2;i>=0;i--){
if(s[i] == '0')
continue;
if(s[i] > '2'||(s[i] == '2' && s[i+1] > '6'))
ans[i] = ans[i+1];
else ans[i] = ans[i+1] + ans[i+2];
}
return ans[0];
}
};