代码随想录算法训练营第八天| 344.反转字符串、541. 反转字符串II、剑指Offer 05.替换空格 、151.翻转字符串里的单词、剑指Offer58-II.左旋转字符串

344.反转字符串

代码随想录

思路:

双指针,从char[]两端出发,交换字符。

代码:

class Solution {
    public void reverseString(char[] s) {
        for(int i = 0, j = s.length - 1; i < j; i++, j--){
            s[i] ^= s[j];
            s[j] ^= s[i];
            s[i] ^= s[j];
        }
    }
}

需要注意的点:

1、学会用位运算交换的方法。

541. 反转字符串II

代码随想录

思路:

代码:

class Solution {
    public String reverseStr(String s, int k) {
        //string转化为char[]方便修改
        char[] c = s.toCharArray();
        for(int i = 0; i < c.length; i += 2 * k){
            //如果剩余字符少于k,全部反转
            reverse(c, i, Math.min(c.length - 1, i + k - 1));
        }
        return new String(c);
    }

    private void reverse(char[] c, int start, int end){
        for(int i = start, j = end; i < j; i++, j--){
            c[i] ^= c[j];
            c[j] ^= c[i];
            c[i] ^= c[j];
        }
    }
}

需要注意的点:

剑指Offer 05.替换空格

代码随想录

Stringbuilder:深入理解String、StringBuffer和StringBuilder_有头发的代码匠的博客-CSDN博客_stringbuilder内存结构

思路:

主要学会用双指针,无需额外空间。

在原字符串后加上2倍其空格数的空格,成为需要返回新字符串,用left指针指向原字符串的结尾,right指向新字符串的结尾,当遇到空格就补充‘20%’,从后向前更新两个指针,直至字符串开始(都是在转化成char[] 的基础上进行的)

代码:

1:新建数组存储

class Solution {
    public String replaceSpace(String s) {
        StringBuilder res = new StringBuilder();
        for(int i = 0; i < s.length(); i++){
            if(s.charAt(i) != ' '){
                res.append(s.charAt(i));
            }else{
                res.append("%20");
            }
        }
        return res.toString();
    }
}

2:双指针更新

class Solution {
    public String replaceSpace(String s) {
        if(s == null || s.length() == 0){
            return s;
        }
        StringBuilder str = new StringBuilder();
        //str用于扩容s
        for(int i = 0; i < s.length(); i++){
            if(s.charAt(i) == ' '){
                str.append("  ");
            }
        }
        //如果没有空格,直接返回s
        if(str.length() == 0){
            return s;
        }
        int left = s.length() - 1;
        s += str.toString();
        int right = s.length() - 1;
        char[] c = s.toCharArray();
        while(right >= 0){
            if(c[left] == ' '){
                c[right--] = '0';
                c[right--] = '2';
                c[right] = '%';
            }else{
                c[right] = c[left];
            }
            left--;
            right--;
        }
        return new String(c);
    }
}

需要注意的点:

1、原字符串每有一个空格需要增加的空格数为2,而不是3(因为已经有一个空格)。

2、修改字符串(s)中的值,先转成char[](s.toCharArray()),再修改,最后转成string(String(char[] c))。

151.翻转字符串里的单词

代码随想录

思路:

见代码。

代码:

class Solution {
    public String reverseWords(String s) {
        char[] c = s.toCharArray();
        //整个字符串反转
        reverse(c, 0, c.length - 1);
        int k = 0;
        for(int i = 0; i < c.length; i++){
            if(c[i] == ' '){
                continue;
            }
            int start = i;
            //此处尽管在大循环内,
            //但只能保证i进入此循环时是<c.length的,
            //不能保证i++之后还在此范围内
            while(i < c.length && c[i] != ' '){
                i++;
            }
            int end = i - 1;
            //反转找到的单词
            reverse(c, start, end);
            //向前移位
            for(int j = start; j < i;j++){
                c[k++] = c[j]; 
            }
            //每个单词后加一个空格
            if(k < c.length){
                c[k++] = ' ';
            }
        }
        return new String(c, 0, c[k - 1] != ' ' ? k : k - 1);        
    }



    private void reverse(char[] c, int start, int end){
        for(int i = start, j = end; i < j; i++, j--){
            c[i] ^= c[j];
            c[j] ^= c[i];
            c[i] ^= c[j];
        }
    }
}

需要注意的点:

1、注意所有下标都不能超过字符串的长度。

2、最后可能出现多余空格,注意截取。

剑指Offer58-II.左旋转字符串

代码随想录

思路:

见代码注释。

代码:

class Solution {
    public String reverseLeftWords(String s, int n) {
        char[] c = s.toCharArray();
        //分为三步:1、反转前n个字符;2、反转其余字符;3、反转整个字符串
        reverse(c, 0, n - 1);
        reverse(c, n, c.length - 1);
        reverse(c, 0, c.length - 1);
        return new String(c);
    }


    private void reverse(char[] c, int start, int end){
        for(int i = start, j = end; i < j; i++, j--){
            c[i] ^= c[j];
            c[j] ^= c[i];
            c[i] ^= c[j];
        }
    }
}

需要注意的点:

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值