【算法第六天7.19】反转字符串,反转字符串||,剑指 Offer 05. 替换空格,反转字符串的单词, 左旋转字符串

链接力扣344-反转字符串

链接力扣541-反转字符串||

链接剑指 Offer 05. 替换空格

链接力扣151- 反转字符串的单词

链接剑指 Offer 58 - II. 左旋转字符串

================================================

链接力扣344-反转字符串

思路:以中间为分界线,左右两个边界交换字符,依次向里收缩

java 复制代码
class Solution {
    public void reverseString(char[] s) {
        int n = s.length;
        for(int i = 0, j = n-1; i<j; i++,j--){
            char tmp = s[i];
            s[i] = s[j];
            s[j] = tmp;
        }
    }
}

链接力扣541-反转字符串||

思路

首先:字符串转化为字符数组

char[] res = s.toCharArray();

最后:将数组再转回字符串

return new String(res);

1、循环以2k为单位,

2、在这个2k长的数组中进行反转,需要有首尾索引

3、start就是i,end在循环过程中为i+k-1,如果到数组最后且不够k个,直接将length-1作为尾

java 复制代码
class Solution {
    public String reverseStr(String s, int k) {
        // 字符串转化为字符数组
        char[] res = s.toCharArray();
        // 这段的逻辑:
        // 1、循环以2k为单位,
        // 2、在这个2k长的数组中进行反转,需要有首尾索引
        // 3、start就是i,end在循环过程中为i+k-1,如果到数组最后且不够k个,直接将length-1作为尾
        for(int i = 0; i < res.length; i += 2*k){
            int start = i;
            int end = Math.min(start + k - 1, res.length-1);
            reverse(res,start,end);
        }
        return new String(res);
    }
    public char[] reverse(char[] ch,int i,int j){
        int n = ch.length;
        while(i < j){
            char tmp = ch[i];
            ch[i] = ch[j];
            ch[j] = tmp;
            i++;
            j--;
        }
        return ch;
    }
}

链接剑指 Offer 05. 替换空格

思路

循环过程中,都把字符串转为了字符数组,这样方便遍历

使用双指针方法,不使用额外空间

1、用StringBuider先把需要增加的空间给算出来

2、用两个指针:left指向旧字符串的末尾,right指向新字符串的末尾

一旦遇到旧字符的空位,新字符串需要加'0','2','%'这三个字符;

如果没遇到空位,则直接让新串right=旧串left;

最后再进行left--;right--

3、特殊情况:s串为空或者长度为0;遍历之后,发现s串中没有空格(需要添加的)

java 复制代码
class Solution {
    public String replaceSpace(String s) {
        // 如果s为空或者长度为0
        if(s == null || s.length() == 0) return s;
        char[] arr = s.toCharArray();
        StringBuilder str = new StringBuilder();
        for(int i = 0; i < arr.length; i++){
            if(arr[i] == ' '){
                str.append("  ");
            }
        }
        // 如果str为0,则说明原字符串无空格
        if(str.length() == 0) return s;
        int left = s.length()-1;
        //串的拼接
        s += str.toString();
        int right = s.length()-1;
        char[] ch = s.toCharArray();
        //循环条件:旧串一直到最前面一个
        while(left >= 0){
            if(ch[left] ==' '){
                ch[right--] = '0';
                ch[right--] = '2';
                ch[right] = '%';
            }else{
                ch[right] = ch[left];
            }
            left--;
            right--;
        }
        //最后,将字符数组直接放入String中
        return new String(ch);
    }
}

链接力扣151- 反转字符串的单词

思路

1、先处理单词中可能的多余空格

2、整个串全部反转

3、串中的单词逐个反转回来

java 复制代码
class Solution {
    public String reverseWords(String s) {
        StringBuilder sb = removeSpace(s);
        reverseString(sb,0,sb.length()-1);
        reEachWord(sb);
        return sb.toString();
    }

    private StringBuilder removeSpace(String s){
        int start = 0;
        int end = s.length() - 1;
        //删除前后位置的空格
        while (s.charAt(start) == ' ') start++;
        while (s.charAt(end) == ' ') end--;
        StringBuilder sb = new StringBuilder();
        while(start <= end){
            char c = s.charAt(start);
            // 下面的循环可以保证每个单词间只有一个空格
            // if的第一个条件,保证空格前的单词可以进入sb中,
            // 当c == ' '时,第二个条件发挥作用
            // if的第二个条件,保证单词与单词间只有一个空格
            // 当c == ' '且sb.charAt(sb.length() - 1) == ' '时,则说明有多余的空格,start需要++
            if(c != ' ' || sb.charAt(sb.length() - 1) != ' '){
                sb.append(c);
            }
            start++;
        }
        return sb;
    }

/**
     * 反转字符串指定区间[start, end]的字符
     */
    public void reverseString(StringBuilder sb, int start, int end) {
        // System.out.println("ReverseWords.reverseString() called with: sb = [" + sb + "], start = [" + start + "], end = [" + end + "]");
        while (start < end) {
            char temp = sb.charAt(start);
            sb.setCharAt(start, sb.charAt(end));
            sb.setCharAt(end, temp);
            start++;
            end--;
        }
        // System.out.println("ReverseWords.reverseString returned: sb = [" + sb + "]");
    }

    private void reEachWord(StringBuilder sb){
        int start = 0;
        int end = 1;
        int n = sb.length();
        // 第一个遍历:整个带空格的字符串的遍历
        while(start < n){
            // 第二个遍历:对每个单词进行遍历
            // 直到遍历到end为空结束
            while(end < n && sb.charAt(end) != ' '){
                end++;
            }
            // end - 1 是因为end现在指向的是空
            reverseString(sb,start,end-1);
            // end为空,+1是下一个单词的开始
            start = end + 1;
            end = start + 1;
        }
    }
}

链接剑指 Offer 58 - II. 左旋转字符串

思路

用substring的思路 :将前n个存到sb串中,把前几个截走,再接上sb串
不用substring的思路:先反转前n个,再反转后面的,最后整体反转一次

使用substring()

java 复制代码
class Solution {
    public String reverseLeftWords(String s, int n) {
        StringBuilder sb = new StringBuilder();
        for(int i = 0; i < n; i++){
            sb.append(s.charAt(i));
        }
        String newstr = s.substring(n);
        newstr += sb.toString();
        return newstr;
    }
}

三次反转代码

java 复制代码
class Solution {
    public String reverseLeftWords(String s, int n) {
        int len=s.length();
        StringBuilder sb=new StringBuilder(s);
        reverseString(sb,0,n-1);
        reverseString(sb,n,len-1);
        return sb.reverse().toString();
    }
     public void reverseString(StringBuilder sb, int start, int end) {
        while (start < end) {
            char temp = sb.charAt(start);
            sb.setCharAt(start, sb.charAt(end));
            sb.setCharAt(end, temp);
            start++;
            end--;
            }
        }
}
相关推荐
penguin_bark几秒前
69. x 的平方根
算法
这可就有点麻烦了10 分钟前
强化学习笔记之【TD3算法】
linux·笔记·算法·机器学习
救救孩子把11 分钟前
深入理解 Java 对象的内存布局
java
DY009J11 分钟前
深度探索Kali Linux的精髓与实践应用
linux·运维·服务器
落落落sss13 分钟前
MybatisPlus
android·java·开发语言·spring·tomcat·rabbitmq·mybatis
苏宸啊16 分钟前
顺序表及其代码实现
数据结构·算法
万物皆字节19 分钟前
maven指定模块快速打包idea插件Quick Maven Package
java
lin zaixi()19 分钟前
贪心思想之——最大子段和问题
数据结构·算法
FindYou.20 分钟前
C - Separated Lunch
算法·深度优先
夜雨翦春韭26 分钟前
【代码随想录Day30】贪心算法Part04
java·数据结构·算法·leetcode·贪心算法