题目:

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

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

Given an encoded message containing digits, determine the total number of ways to decode it.

For example,
Given encoded message "12", it could be decoded as "AB" (1 2) or "L" (12).

The number of ways decoding "12" is 2.

链接: http://leetcode.com/problems/decode-ways/

题解:

一看到这题就想到了爬楼梯climb stairs,典型的一维DP。下面就用一维DP来做。先建立数组dp = new int[s.length() + 1], 初始化一个数字的情况dp[0] = 1, 两个数字组成一个两位数字的情况dp[1] = 1。接下来写出循环体,先算一个数字的情况,当s.charAt(i - 1)不为0的时候,dp[i] = dp[i - 1], 否则dp[i] = 0。 接下来考虑两位数字,当由i-2和i-1这两位组成的数字大于等于10,小于等于26时,dp[i] += dp[i - 2], 否则忽略此种情况。

Time Complexity - O(n), Space Complexity - O(n)。

public class Solution {
public int numDecodings(String s) {
if(s == null || s.length() == 0 || s.charAt(0) == '0')
return 0;
int[] dp = new int[s.length() + 1];
dp[0] = 1;
dp[1] = 1; for(int i = 2; i < dp.length; i++) {
int num = Integer.parseInt(s.substring(i - 2, i));
int twoStepsBehind = (num <= 26 && num >= 10) ? dp[i - 2] : 0;
int oneStepBehind = s.charAt(i - 1) != '0' ? dp[i - 1] : 0;
dp[i] = twoStepsBehind + oneStepBehind;
} return dp[s.length()];
}
}

可以继续优化Space Complexity至O(1).

public class Solution {
public int numDecodings(String s) {
if(s == null || s.length() == 0 || s.charAt(0) == '0')
return 0; int first = 1;
int second = 1; for(int i = 2; i < s.length() + 1; i++) {
int num = Integer.parseInt(s.substring(i - 2, i));
int twoStepsBehind = (num >= 10 && num <= 26) ? first : 0;
int oneStepBehind = s.charAt(i - 1) != '0' ? second : 0;
first = second;
second = twoStepsBehind + oneStepBehind;
} return second;
}
}

题外话: 使用DP思想的一些题目 - decode ways, climb stairs, find LCS(longest common subsequence), find longest ascending subsequence, fine longest descending subsequens, 背包问题,poj滑雪,等等。DP这种重要的编程思想要好好学习领会。

二刷:

还是使用dp,新建一个dp数组比较好理解,但空间的优化却不是很熟练。对于dp,还是需要加强狠练。如何才能写出优雅而且精炼的代码是个问题。 Elegant and concise

Java:

Time Complexity - O(n), Space Complexity - O(n)。

public class Solution {
public int numDecodings(String s) {
if (s == null || s.length() == 0 || s.charAt(0) == '0') {
return 0;
}
int len = s.length();
int[] numWays = new int[len + 1];
numWays[0] = 1; // empty string
numWays[1] = 1; // one char
for (int i = 2; i <= len; i++) {
int num = Integer.parseInt(s.substring(i - 2, i));
numWays[i] = (num <= 26 && num >= 10) ? numWays[i - 2] : 0;
numWays[i] += (s.charAt(i - 1) != '0') ? numWays[i - 1] : 0;
}
return numWays[len];
}
}

因为do[i] 只和dp[i - 1]以及dp[i - 2]有关,我们可以优化空间到O(1)。就是使用两个变量来代表numWays[i - 1]和numWays[i - 2], 以及一个变量res来代表它们的和,接下来三个一起倒腾倒腾就好了

Time Complexity - O(n), Space Complexity - O(1)。

public class Solution {
public int numDecodings(String s) {
if (s == null || s.length() == 0 || s.charAt(0) == '0') {
return 0;
}
int len = s.length();
int lastTwoSteps = 1; // empty string
int lastOneStep = 1; // one char
int res = 0;
for (int i = 2; i <= len; i++) {
int num = Integer.parseInt(s.substring(i - 2, i));
res += (num <= 26 && num >= 10) ? lastTwoSteps : 0;
res += (s.charAt(i - 1) != '0') ? lastOneStep : 0;
lastTwoSteps = lastOneStep;
lastOneStep = res;
res = 0;
}
return lastOneStep;
}
}

题外话:

2/11/2016:

时间相当紧张,要复习LC,刷面经,多线程,设计模式,系统设计。自己提速却不是很成功,转进努力吧。要深入思考。

自己与去年9月开始刷题以来,有什么改变和进步呢??? 好像并没有实质性的突破....要说进步的地方,可能就是养成了学习的习惯吧

Reference:

https://leetcode.com/discuss/49719/dp-with-easy-understand-java-solution

https://leetcode.com/discuss/8527/dp-solution-java-for-reference

91. Decode Ways的更多相关文章

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

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

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

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

  3. 【LeetCode】91. Decode Ways 解题报告(Python)

    [LeetCode]91. Decode Ways 解题报告(Python) 标签(空格分隔): LeetCode 作者: 负雪明烛 id: fuxuemingzhu 个人博客: http://fux ...

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

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

  5. 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 ...

  6. 91. Decode Ways反编译字符串

    [抄题]: A message containing letters from A-Z is being encoded to numbers using the following mapping: ...

  7. leetcode 91 Decode Ways ----- java

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

  8. 【LeetCode】91. Decode Ways

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

  9. 【一天一道LeetCode】#91. Decode Ways

    一天一道LeetCode 本系列文章已全部上传至我的github,地址:ZeeCoder's Github 欢迎大家关注我的新浪微博,我的新浪微博 欢迎转载,转载请注明出处 (一)题目 A messa ...

随机推荐

  1. 关于mysql group_concat 不能显示为空的列的其他信息

    今天做项目遇到一个问题,百度好久都没找到问题所在 是酱紫的,一张表 关联的表 然后我用sql语句查询 point.pid,point.pname,GROUP_CONCAT(downsite.pname ...

  2. PHP 魔术方法(所有的魔术方法)

    慢慢长寻夜,明月高空挂. 目前PHP所有的魔术方法有一下这些 __construct() __destruct() __call() __callStatic() __get() __set() __ ...

  3. javascript之高级函数应用思想

    1.级联函数:应用对象方法调用的连写 function A(){ this.a = ''; this.b = ''; this.c = ''; } //改造一下 A.prototype = { A.p ...

  4. Sublime Text 前端插件推荐

    html/CSS快速编辑 --- Emment HTML CSS JS 美化插件 --- HTML/CSS/JS Prettyfy MarkDown 预览 --- MarkDown Preview J ...

  5. php错误消息捕获

    <?php header('Content-type:text/html;charset=UTF-8'); //function_exists('ini_set') && ini ...

  6. PHP的$_SERVER['HTTP_HOST']获取服务器地址功能详解,$_SERVER['HTTP_X_FORWARDED_HOST']

    uchome的index文件中的二级域名功能判断,使用了php的$_SERVER['HTTP_HOST'],开始对这个不是很了解,所以百度了一下,发现一篇帖子有点意思,转发过来做个记录. 在php中, ...

  7. Ajax的理解

    初学JS,一直认为Ajax是个很高级的.不可亵玩的东西.这两天怀着忐忑的心情接触了一下它, 感觉它并没有想象中的那么难理解. 其实,Ajax就是浏览器端向服务器请求资源的一个对象(方法). 就跟打电话 ...

  8. js 操作cookie

    jquery.cookie中的操作: jquery.cookie.js是一个基于jquery的插件,点击下载! 创建一个会话cookie: $.cookie(‘cookieName’,'cookieV ...

  9. The method of type must override a superclass method

    导入android项目时,报The method of type must override asuperclass method 一堆错误, 解决方法: 将编译的jdk与使用的jdk版本一致即可.

  10. liunx命令之whereis、which、find的区别和联系

    liunx命令之whereis.which.find的区别和联系