A message containing letters from A-Z is being encoded to numbers using the following mapping way:

'A' -> 1
'B' -> 2
...
'Z' -> 26

Beyond that, now the encoded string can also contain the character '*', which can be treated as one of the numbers from 1 to 9.

Given the encoded message containing digits and the character '*', return the total number of ways to decode it.

Also, since the answer may be very large, you should return the output mod 109 + 7.

Example 1:

Input: "*"
Output: 9
Explanation: The encoded message can be decoded to the string: "A", "B", "C", "D", "E", "F", "G", "H", "I". 

Example 2:

Input: "1*"
Output: 9 + 9 = 18

Note:

  1. The length of the input string will fit in range [1, 105].
  2. The input string will only contain the character '*' and digits '0' - '9'.

91. Decode Ways  的拓展,这次字符串里面可能含有'*', 它可以1~9中的任何一个,求总的解码方法数。

解法:还是DP,主要是如何处理'*'。

Java:

    public int numDecodings(String s) {
/* initial conditions */
long[] dp = new long[s.length()+1];
dp[0] = 1;
if(s.charAt(0) == '0'){
return 0;
}
dp[1] = (s.charAt(0) == '*') ? 9 : 1; /* bottom up method */
for(int i = 2; i <= s.length(); i++){
char first = s.charAt(i-2);
char second = s.charAt(i-1); // For dp[i-1]
if(second == '*'){
dp[i] += 9*dp[i-1];
}else if(second > '0'){
dp[i] += dp[i-1];
} // For dp[i-2]
if(first == '*'){
if(second == '*'){
dp[i] += 15*dp[i-2];
}else if(second <= '6'){
dp[i] += 2*dp[i-2];
}else{
dp[i] += dp[i-2];
}
}else if(first == '1' || first == '2'){
if(second == '*'){
if(first == '1'){
dp[i] += 9*dp[i-2];
}else{ // first == '2'
dp[i] += 6*dp[i-2];
}
}else if( ((first-'0')*10 + (second-'0')) <= 26 ){
dp[i] += dp[i-2];
}
} dp[i] %= 1000000007;
}
/* Return */
return (int)dp[s.length()];
} 

Python:

class Solution(object):
def numDecodings(self, s):
"""
:type s: str
:rtype: int
"""
if len(s) == 0 or s[0] == '0':
return 0 dp = [0] * (len(s) + 1)
dp[0] = 1
dp[1] = 9 if s[0] == '*' else 1 for i in xrange(2, len(dp)):
first = s[i-2]
second = s[i-1]
# for dp[i-1]
if second == '*':
dp[i] = dp[i-1] * 9
elif second != '0':
dp[i] = dp[i-1] # for dp[i-2]
if first == '*':
if second == '*':
dp[i] += 15 * dp[i-2]
elif second <= '6':
dp[i] += 2 * dp[i-2]
else:
dp[i] += dp[i-2]
elif first == '1' or first == '2':
if second == '*':
if first == '1':
dp[i] += 9 * dp[i-2]
else:
dp[i] += 6 * dp[i-2]
elif first == '1' or (first == '2' and second <= '6'):
dp[i] += dp[i-2] dp[i] %= 1000000007 return dp[-1]   

Python:

class Solution(object):
def numDecodings(self, s):
"""
:type s: str
:rtype: int
"""
M, W = 1000000007, 3
dp = [0] * W
dp[0] = 1
dp[1] = 9 if s[0] == '*' else dp[0] if s[0] != '0' else 0
for i in xrange(1, len(s)):
if s[i] == '*':
dp[(i + 1) % W] = 9 * dp[i % W]
if s[i - 1] == '1':
dp[(i + 1) % W] = (dp[(i + 1) % W] + 9 * dp[(i - 1) % W]) % M
elif s[i - 1] == '2':
dp[(i + 1) % W] = (dp[(i + 1) % W] + 6 * dp[(i - 1) % W]) % M
elif s[i - 1] == '*':
dp[(i + 1) % W] = (dp[(i + 1) % W] + 15 * dp[(i - 1) % W]) % M
else:
dp[(i + 1) % W] = dp[i % W] if s[i] != '0' else 0
if s[i - 1] == '1':
dp[(i + 1) % W] = (dp[(i + 1) % W] + dp[(i - 1) % W]) % M
elif s[i - 1] == '2' and s[i] <= '6':
dp[(i + 1) % W] = (dp[(i + 1) % W] + dp[(i - 1) % W]) % M
elif s[i - 1] == '*':
dp[(i + 1) % W] = (dp[(i + 1) % W] + (2 if s[i] <= '6' else 1) * dp[(i - 1) % W]) % M
return dp[len(s) % W] 

C++:

class Solution {
public:
int numDecodings(string s) {
int n = s.size(), M = 1e9 + 7;
vector<long> dp(n + 1, 0);
dp[0] = 1;
if (s[0] == '0') return 0;
dp[1] = (s[0] == '*') ? 9 : 1;
for (int i = 2; i <= n; ++i) {
if (s[i - 1] == '0') {
if (s[i - 2] == '1' || s[i - 2] == '2') {
dp[i] += dp[i - 2];
} else if (s[i - 2] == '*') {
dp[i] += 2 * dp[i - 2];
} else {
return 0;
}
} else if (s[i - 1] >= '1' && s[i - 1] <= '9') {
dp[i] += dp[i - 1];
if (s[i - 2] == '1' || (s[i - 2] == '2' && s[i - 1] <= '6')) {
dp[i] += dp[i - 2];
} else if (s[i - 2] == '*') {
dp[i] += (s[i - 1] <= '6') ? (2 * dp[i - 2]) : dp[i - 2];
}
} else { // s[i - 1] == '*'
dp[i] += 9 * dp[i - 1];
if (s[i - 2] == '1') dp[i] += 9 * dp[i - 2];
else if (s[i - 2] == '2') dp[i] += 6 * dp[i - 2];
else if (s[i - 2] == '*') dp[i] += 15 * dp[i - 2];
}
dp[i] %= M;
}
return dp[n];
}
};  

C++:

class Solution {
public:
int numDecodings(string s) {
long e0 = 1, e1 = 0, e2 = 0, f0, f1, f2, M = 1e9 + 7;
for (char c : s) {
if (c == '*') {
f0 = 9 * e0 + 9 * e1 + 6 * e2;
f1 = e0;
f2 = e0;
} else {
f0 = (c > '0') * e0 + e1 + (c <= '6') * e2;
f1 = (c == '1') * e0;
f2 = (c == '2') * e0;
}
e0 = f0 % M;
e1 = f1;
e2 = f2;
}
return e0;
}
};

  

类似题目:

[LeetCode] 91. Decode Ways 解码方法

All LeetCode Questions List 题目汇总

[LeetCode] 639. Decode Ways II 解码方法 II的更多相关文章

  1. leetcode 639 Decode Ways II

    首先回顾一下decode ways I 的做法:链接 分情况讨论 if s[i]=='*' 考虑s[i]单独decode,由于s[i]肯定不会为0,因此我们可以放心的dp+=dp1 再考虑s[i-1] ...

  2. LeetCode OJ:Decode Ways(解码方法)

    A message containing letters from A-Z is being encoded to numbers using the following mapping: 'A' - ...

  3. leetcode 91 Decode Ways I

    令dp[i]为从0到i的总方法数,那么很容易得出dp[i]=dp[i-1]+dp[i-2], 即当我们以i为结尾的时候,可以将i单独作为一个字母decode (dp[i-1]),同时也可以将i和i-1 ...

  4. Leetcode 91. Decode Ways 解码方法(动态规划,字符串处理)

    Leetcode 91. Decode Ways 解码方法(动态规划,字符串处理) 题目描述 一条报文包含字母A-Z,使用下面的字母-数字映射进行解码 'A' -> 1 'B' -> 2 ...

  5. leetcode@ [91] Decode Ways (Dynamic Programming)

    https://leetcode.com/problems/decode-ways/ A message containing letters from A-Z is being encoded to ...

  6. [LeetCode] Decode Ways II 解码方法之二

    A message containing letters from A-Z is being encoded to numbers using the following mapping way: ' ...

  7. [LeetCode] 91. Decode Ways 解码方法

    A message containing letters from A-Z is being encoded to numbers using the following mapping: 'A' - ...

  8. leetcode[90] Decode Ways

    题目:如下对应关系 'A' -> 1 'B' -> 2 ... ‘Z’ -> 26 现在给定一个字符串,返回有多少种解码可能.例如:Given encoded message &qu ...

  9. LeetCode(91):解码方法

    Medium! 题目描述: 一条包含字母 A-Z 的消息通过以下方式进行了编码: 'A' -> 1 'B' -> 2 ... 'Z' -> 26 给定一个只包含数字的非空字符串,请计 ...

随机推荐

  1. 小白式Git使用教程,从0到1

    Git是什么? Git是目前世界上最先进的分布式版本控制系统.工作原理 / 流程: Workspace:工作区 Index / Stage:暂存区 Repository:仓库区(或本地仓库) Remo ...

  2. D. Zero Quantity Maximization ( Codeforces Round #544 (Div. 3) )

    题目链接 参考题解 题意: 给你 整形数组a 和 整形数组b ,要你c[i] = d * a[i] + b[i], 求  在c[i]=0的时候  相同的d的数量 最多能有几个. 思路: 1. 首先打开 ...

  3. 【转载】linux性能监控分析及通过nmon_analyse生成分析报表

    转载地址:http://www.cnblogs.com/Lam7/p/6604832.html nmon是一款分析 AIX 和 Linux 性能的免费工具 nmon 工具还可以将相同的数据捕获到一个文 ...

  4. Python中单引号、双引号、三引号的区别

    在学习python中的sqlite时发现实例的语句创建表时是用的三个单引号,但其他的表操作语句都是双引号,就不明白,于是搜了一下,在此做一下笔记. import sqlite3 conn = sqli ...

  5. oracle 将与本端(name)联系的人取出

    本人与其他所有人认识的SQL: 首先新建测试表 create table DIM_IA_TEST6 ( NAME ), OTHERNAME ) ) 插入数据 --如果没有重复的记录,则不用去重使用un ...

  6. centos7中,mysql连接报错:1130 - Host ‘118.111.111.111’ is not allowed to connect to this MariaDB server

    客户端连接报错 这个问题是因为用户在数据库服务器中的mysql数据库中的user的表中没有权限. 解决步骤 1.连接服务器: mysql -u root -p 2.看当前所有数据库:show data ...

  7. P3232 [HNOI2013]游走——无向连通图&&高斯消元

    题意 一个无向连通图,顶点从1编号到N,边从1编号到M. 小Z在该图上进行随机游走,初始时小Z在1号顶点,每一步小Z以相等的概率随机选 择当前顶点的某条边,沿着这条边走到下一个顶点,获得等于这条边的编 ...

  8. centos7.2(二)搭建lamp(Apache+PHP+Mysql环境)教程

    开始安装前,看说明. 说明0  查看服务器是否能被ssh登陆 http://tool.chinaz.com/port/ 如果显示关闭,说明被大陆封闭了,删除服务器重新建立一个. 说明1:Centos7 ...

  9. ajax 样式

    Ajax 由 HTML.JavaScript™ 技术.DHTML 和 DOM 组成,这一杰出的方法可以将笨拙的 Web 界面转化成交互性的 Ajax 应用程序.它是一种构建网站的强大方法. 使用aja ...

  10. java之大文件分段上传、断点续传

    文件上传是最古老的互联网操作之一,20多年来几乎没有怎么变化,还是操作麻烦.缺乏交互.用户体验差. 一.前端代码 英国程序员Remy Sharp总结了这些新的接口 ,本文在他的基础之上,讨论在前端采用 ...