剑指 Offer - 字符串合辑

🍎道阻且长,行则将至。🍓

🌻算法,不如说它是一种思考方式🍀


算法专栏: 👉🏻123


一、🌱剑指 Offer 05. 替换空格

  • 题目描述:请实现一个函数,把字符串 s 中的每个空格替换成"%20"。
  • 来源:力扣(LeetCode)
  • 难度:简单
  • 提示:
    0 <= s 的长度 <= 10000
  • 示例 1:
    输入:s = “We are happy.”
    输出:“We%20are%20happy.”

🌴解题

  1. 字符数组
class Solution {
    public String replaceSpace(String s) {
        int num=0;
        for (int i = 0; i < s.length(); i++) {
            if(s.charAt(i)==' ')
                num++;
        }
        char[] ans=new char[s.length()+(num*2)];

        num=0;
        for (int i = 0; i < s.length(); i++) {
            if(s.charAt(i)!=' '){
                ans[num]=s.charAt(i);
                num++;
            }if(s.charAt(i)==' '){
                ans[num]='%';num++;
                ans[num]='2';num++;
                ans[num]='0';num++;
            }
        }
        return new String(ans);
    }
}
  1. 可变字符串
class Solution {
    public String replaceSpace(String s) {
        StringBuilder ans = new StringBuilder();
        for(Character c : s.toCharArray())
        {
            if(c == ' ') ans.append("%20");
            else ans.append(c);
        }
        return ans.toString();
    }
}

在这里插入图片描述


二、🌱剑指 Offer 58 - II. 左旋转字符串

  • 题目描述:字符串的左旋转操作是把字符串前面的若干个字符转移到字符串的尾部。请定义一个函数实现字符串左旋转操作的功能。比如,输入字符串"abcdefg"和数字2,该函数将返回左旋转两位得到的结果"cdefgab"。

  • 来源:力扣(LeetCode)

  • 难度:简单

  • 示例 1:
    输入: s = “abcdefg”, k = 2
    输出: “cdefgab”
    示例 2:
    输入: s = “lrloseumgh”, k = 6
    输出: “umghlrlose”

  • 提示:
    1 <= k < s.length <= 10000

🌴解题

  1. 自己写反转,反过来再反过来反过来😂
class Solution {
        public String reverseLeftWords(String s, int n) {
        StringBuilder ns=new StringBuilder(s);
        reverseString(ns,0,s.length()-1);

        reverseString(ns,0,s.length()-n-1);
        reverseString(ns,s.length()-n,s.length()-1);
        return ns.toString();
    }

    private static void reverseString(StringBuilder ns, int i, int length) {
        while (i<length){
            char tem= ns.charAt(i);
            ns.setCharAt(i,ns.charAt(length));
            ns.setCharAt(length,tem);
            i++;length--;
        }
    }
}

在这里插入图片描述

  1. 直接使用API
class Solution {
    public String reverseLeftWords(String s, int n) {
        return s.substring(n,s.length())+s.substring(0,n);
    }
}

在这里插入图片描述


三、🌱剑指 Offer 20. 表示数值的字符串

  • 题目描述:请实现一个函数用来判断字符串是否表示数值(包括整数和小数)。
    数值(按顺序)可以分成以下几个部分:
     1.若干空格
     2.一个 小数 或者 整数
     3.(可选)一个 ‘e’ 或 ‘E’ ,后面跟着一个 整数
     4.若干空格
    小数(按顺序)可以分成以下几个部分:
     1.(可选)一个符号字符(‘+’ 或 ‘-’)
     2.下述格式之一:
      2.1至少一位数字,后面跟着一个点 ‘.’
      2.2至少一位数字,后面跟着一个点 ‘.’ ,后面再跟着至少一位数字
      2.3一个点 ‘.’ ,后面跟着至少一位数字
    整数(按顺序)可以分成以下几个部分:
     1.(可选)一个符号字符(‘+’ 或 ‘-’)
     2.至少一位数字
    部分数值列举如下
    [“+100”, “5e2”, “-123”, “3.1416”, “-1E-16”, “0123”]
    部分非数值列举如下
    [“12e”, “1a3.14”, “1.2.3”, “±5”, “12e+5.4”]

  • 来源:力扣(LeetCode)

  • 难度:中等

  • 提示:
    1 <= s.length <= 20
    s 仅含英文字母(大写和小写),数字(0-9),加号 ‘+’ ,减号 ‘-’ ,空格 ’ ’ 或者点 ‘.’ 。

🌴解题

  • 只能说,很复杂!
class Solution {
    public boolean isNumber(String s) {
        boolean ans=false;
        int len=s.length();
        int dot=0,e=0;// .  e  次数
        int loce=len+1;// e 的位置
        for(int i=0;i<len;i++){
            //err 字符
            if(s.charAt(i)<'0'||s.charAt(i)>'9'){
                if(s.charAt(i)!=' '&&s.charAt(i)!='+'&&s.charAt(i)!='-'&&s.charAt(i)!='e'&&s.charAt(i)!='E'&&s.charAt(i)!='.')
                    return false;
            }
            if(s.charAt(i)>='0'&&s.charAt(i)<='9'){
                ans=true;
            }

            if(s.charAt(i)=='.'){
                if(i>loce)
                    return false;
                dot++;
                if(dot>1)// . .
                    return false;
                if(i==0&&i==len-1)
                    return false;
                
                //.前或后非数字
                if((i==0 && (s.charAt(i+1)<'0'||s.charAt(i+1)>'9')))
                    return false;
                if((i>0 && (s.charAt(i-1)<'0'||s.charAt(i-1)>'9'))
                        &&
                        (i<len-1 && (s.charAt(i+1)<'0'||s.charAt(i+1)>'9')))
                    return false;
            }

            if(s.charAt(i)=='e'||s.charAt(i)=='E'){
                if(i==0)return false;
                e++;
                if(e>1)
                    return false;
                loce=i;
                if(i>0&&(s.charAt(i-1)<'0'||s.charAt(i-1)>'9')&&s.charAt(i-1)!='.')
                    return false;
                if(i==len-1)
                    return false;
                if((s.charAt(i+1)!='+' && s.charAt(i+1)!='-'))
                    if(s.charAt(i+1)<'0'||s.charAt(i+1)>'9')
                    return false;
            }

            if(s.charAt(i)=='+'||s.charAt(i)=='-'){
                if(i!=0)
                    if(s.charAt(i-1)!='e'&&s.charAt(i-1)!='E'&&s.charAt(i-1)!=' ')
                        return false;
                if(i==len-1)
                    return false;
                if(i<len-1&&(s.charAt(i+1)<'0'||s.charAt(i+1)>'9')&&s.charAt(i+1)!='.')
                    return false;

            }

            if(s.charAt(i)==' '){
                //前面有数字 内容
                if(i>0){
                    while(i<len){
                        if(s.charAt(i)!=' ')
                            return false;
                        i++;
                    }
                }
                //first 0
                if(i==0){
                    while(i<len && s.charAt(i)==' ')
                        i++;
                    if(i<len)//空格后有内容
                        i--;
                }
            }
        }

        return ans;
    }
}

在这里插入图片描述

  • 找了个简短的,欣赏欣赏!
class Solution {
    public boolean isNumber(String s) {
            return s.trim().matches("[+-]?((\\d+(\\.\\d+)?)|(\\.\\d+)|(\\d+\\.))([eE][+-]?\\d+)?");
    } 
}

在这里插入图片描述


四、🌱剑指 Offer 67. 把字符串转换成整数

  • 题目描述:写一个函数 StrToInt,实现把字符串转换成整数这个功能。不能使用 atoi 或者其他类似的库函数
    首先,该函数会根据需要丢弃无用的开头空格字符,直到寻找到第一个非空格的字符为止。
    当我们寻找到的第一个非空字符为正或者负号时,则将该符号与之后面尽可能多的连续数字组合起来,作为该整数的正负号;假如第一个非空字符是数字,则直接将其与之后连续的数字字符组合起来,形成整数。
    该字符串除了有效的整数部分之后也可能会存在多余的字符,这些字符可以被忽略,它们对于函数不应该造成影响。
    注意:假如该字符串中的第一个非空格字符不是一个有效整数字符、字符串为空或字符串仅包含空白字符时,则你的函数不需要进行转换。
    在任何情况下,若函数不能进行有效的转换时,请返回 0。
    说明
    假设我们的环境只能存储 32 位大小的有符号整数,那么其数值范围为 [−231, 231 − 1]。如果数值超过这个范围,请返回 INT_MAX (231 − 1) 或 INT_MIN (−231) 。

  • 来源:力扣(LeetCode)

  • 难度:中等

  • 提示:
    本题与主站 8 题相同。

🌴解题

class Solution {
    public int strToInt(String str) {
        if(str.length()==0)return 0;
        boolean negative=false; //false
        List<Integer> list=new ArrayList<>();
        int i = 0;

        if(i==0)//去除空格字符串
        while (i < str.length() && str.charAt(i) == ' ')
            i++;
        if(i==str.length()) return 0;
        if (str.charAt(i)!='+'&&str.charAt(i)!='-'&&(str.charAt(i)<'0'||str.charAt(i)>'9'))
            return 0;//前面出现非数字 字符
        else{
            if(str.charAt(i)=='-') {
                negative = true;i++;
            }else if(str.charAt(i)=='+') {
                negative = false;i++;
            }
            while(i < str.length() && str.charAt(i)!=' '){
                if(str.charAt(i)<='9'&&str.charAt(i)>='0')
                    list.add(str.charAt(i)-'0');
                else break;
                i++;
            }
        }

        if(list.size()==0)return 0;
        int lengthn=0;
        for (int j = 0; j < list.size(); j++) {
            if(j==0&&list.get(j)==0){
                while(j < list.size() && list.get(j)==0)
                    j++;
            }
            lengthn++;
        }
        if(lengthn>11)return (int) (negative?-Math.pow(2,31):(Math.pow(2,31)-1));
        long ans=0,k=1;
        for (int j = 0; j < list.size(); j++) {
            ans+= list.get(list.size()-j-1)*k;
            k=k*10;
            if(!negative && ans>Math.pow(2,31)-1)//正数
                return (int) (Math.pow(2,31)-1);
            if(negative && ans>Math.pow(2,31))//负数
                return (int) (-Math.pow(2,31));
        }
        return (int) (negative?-ans:ans);
    }
}

和上一题比反过来是吧
在这里插入图片描述


🌱 加油!

返回第一页。☝


☕物有本末,事有终始,知所先后。🍭

🍎☝☝☝☝☝我的CSDN☝☝☝☝☝☝🍓

  • 7
    点赞
  • 7
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 10
    评论
评论 10
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

Super algorithm

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值