查看原文
其他

从0打卡leetcode之day9--字符串转整型

帅地 苦逼的码农 2019-05-25

前言

好久没更新了,今天是开学的第一天,这学期选了门算法的课,打算好好刷下《算法导论》这本书,可能接下来会一边分享leetcode的刷题贴,一边分享自己在书上所学的一些算法。欢迎你一起和我学习坚持下去

题目描述

实现 atoi,将字符串转为整数。

在找到第一个非空字符之前,需要移除掉字符串中的空格字符。如果第一个非空字符是正号或负号,选取该符号,并将其与后面尽可能多的连续的数字组合起来,这部分字符即为整数的值。如果第一个非空字符是数字,则直接将其与之后连续的数字字符组合起来,形成整数。

字符串可以在形成整数的字符后面包括多余的字符,这些字符可以被忽略,它们对于函数没有影响。

当字符串中的第一个非空字符序列不是个有效的整数;或字符串为空;或字符串仅包含空白字符时,则不进行转换。

若函数不能执行有效的转换,返回 0。

说明:

假设我们的环境只能存储 32 位有符号整数,其数值范围是 [−231,  231 − 1]。如果数值超过可表示的范围,则返回  INT_MAX (231 − 1) 或 INT_MIN (−231) 。

示例 1:

输入: "42" 输出: 42

示例 2:

输入: "   -42" 输出: -42 解释: 第一个非空白字符为 '-', 它是一个负号。     我们尽可能将负号与后面所有连续出现的数字组合起来,最后得到 -42 。

示例 3:

输入: “4193 with words”
输出: 4193
解释: 转换截止于数字 ‘3’ ,因为它的下一个字符不为数字。

示例 4:

输入: "words and 987" 输出: 0 解释: 第一个非空字符是 'w', 但它不是数字或正、负号。     因此无法执行有效的转换。

示例 5:

输入: "-91283472332" 输出: -2147483648 解释: 数字 "-91283472332" 超过 32 位有符号整数范围。     因此返回 INT_MIN (−231)

解题

说真,有时候遇到这道题目描述很长的题,真的有点不想去看它,读个题意都花了好久,不过这也间接说明了自己刷的题实在是少。偷偷透露一下,有时候都不知道题目要我们干什么…..

刚开始的时候,以为像”0003333aaa”这样的字符串也返回0,提交的时候,根据系统的判断,前面的0也要像空格一样被忽略去掉。

对于这道题,我的想法很简单也很暴力,就是根据题目给的那些条件与限制,一条一条着去判断,虽然这道题不难,但觉得细节是真的挺多的,提交了好几次错误。

就是按照题目说的:

  1. 先去掉空格

  2. 判断正负数

  3. 用一个long的变量来保存目标整数,主要是为了方便判断该整数有没有越界。

直接上代码吧:


public int myAtoi(String str) {
       if(str == null){
           return 0;
       }
       int i = 0;//用来遍历字符串
       int flag = 1;
       long num = 0;

       //去除空格
       while(i < str.length() && str.charAt(i) == ' '){
           i++;
       }
       if(i < str.length() && str.charAt(i) == '-'){
           i++;
           flag = -1;
       }else if(i < str.length() && str.charAt(i) == '+'){
           i++;
           flag = 1;
       }

       while(i < str.length()){
           if(str.charAt(i) <= '9'&&str.charAt(i)>= '0'){
               num = num * 10 + (str.charAt(i) - 48)*flag;
               i++;
           }else{
               break;
           }
           //本来是放到最后来判断的,但是发现这个值还有可能超出long范围
           if(num > Integer.MAX_VALUE){
               return Integer.MAX_VALUE;
           }else if(num < Integer.MIN_VALUE){
               return Integer.MIN_VALUE;
           }
       }
       return (int)num;
   }



本来我是把num放到最后来判断正负数,有没有超出最大整数,但发现题目给出的整数,连long类型也存不下,所以就只能一遍处理一边判断了。

下面是我把这些代码处理了一下,感觉看起来简洁点,也放出来给大家参考,同时欢迎大家能给出更见简洁的代码。


public int myAtoi2(String str) {
       if(str == null )return 0;
       int len = str.length();//由于多次用到,用一个变量存起来
       int i = 0;//用来遍历字符串
       int flag = 1;//用来判断正负数
       long num = 0;//存放目标数
       char[] arr = str.toCharArray();
       //去除空格
       while(i < len && arr[i] == ' ')i++;
       //判断正负数
       if(i < len && (arr[i] == '-' || arr[i] == '+')){
           flag = arr[i]=='-'? -1 : 1;
           i++;
       }
       while(i < len){
           if(arr[i] <= '9'&&arr[i]>= '0'){
               num = num * 10 + (arr[i] - '0')*flag;
               i++;
           }else{
               break;
           }
           //本来是放到最后来判断的,但是发现这个值还有可能超出long范围
           if(num > Integer.MAX_VALUE){
               return Integer.MAX_VALUE;
           }else if(num < Integer.MIN_VALUE){
               return Integer.MIN_VALUE;
           }
       }
       return (int)num;
   }



假如你们有更加优雅的做法,欢迎指点出来。我创建了一个leetcode的讨论群,如果你想进,可以加我微信(公号右下方有我的微信),备注“leetcode”,我拉你进群,不过,貌似这群有点不活跃,哈哈,可能是我没有带动大家….

关注公我的众号:苦逼的码农,获取更多原创文章,后台回复礼包送你一份资源大礼包。同时也感谢把文章介绍给更多需要的人。

点赞与转发是最大的支持

    您可能也对以下帖子感兴趣

    文章有问题?点此查看未经处理的缓存