题目链接:力扣(LeetCode)官网 - 全球极客挚爱的技术成长平台
解题思路:动态规划
- 定义状态:dp[i]表示以s[i]结尾的前i个字符的解码方法数
- 初始状态:如果s[0]=='0',则dp[0]=0,否则dp[0]=1
- 状态转移:对于当前状态dp[i],有两种情况
- s[i]单独解码:如果s[i] != '0',则可将s[i]单独解码与s[0,..., i-1]构成一种解码方式,dp[i] = dp[i-1]
- s[i]与s[i-1]一起解码:如果s[i-1]和s[i]构成的数小于等于26,并且s[i-1]!='0' 则可以一起解码:
- 如果i==1,此时dp[i] +=1
- 否则:即s[i-1,i]一起解码与s[0,i-2]构成一种解码方式,dp[i]+=dp[i-2]
- 最后dp[s.length()-1]即所求结果
AC代码:
class Solution {
public int numDecodings(String s) {
int[] dp = new int[s.length()];
if (s.charAt(0) == '0') {
dp[0] = 0;
} else {
dp[0] = 1;
}
for (int i = 1; i < s.length(); i++) {
char prev = s.charAt(i - 1);
char cur = s.charAt(i);
if(cur!='0'){
dp[i]=dp[i-1];
}
int num = (prev-'0')*10+(cur-'0');
if (num<=26&&prev!='0'){
if (i==1){
dp[i]+=1;
}else {
dp[i]+=dp[i-2];
}
}
}
return dp[s.length() - 1];
}
}
优化:空间压缩,dp[i]的状态之和dp[i-1]和dp[i-2]相关,可以使用两个变量滚动更新记录dp[i-1]和dp[i-2]将空间复杂度优化为O(1)
AC代码:
class Solution {
public int numDecodings(String s) {
int result =0;
if (s.charAt(0) != '0') {
result=1;
}
int firstNum = 0;
int secondNum =result;
for (int i = 1; i < s.length(); i++) {
result=0;
if(s.charAt(i)!='0'){
result=secondNum;
}
int num = (s.charAt(i-1)-'0')*10+(s.charAt(i)-'0');
if (num<=26&&s.charAt(i-1)!='0'){
if (i==1){
result+=1;
}else {
result+=firstNum;
}
}
firstNum=secondNum;
secondNum=result;
}
return result;
}
}