反转字符串中的单词 力扣151

一、题目

        

给你一个字符串 s ,请你反转字符串中 单词 的顺序。

单词 是由非空格字符组成的字符串。s 中使用至少一个空格将字符串中的 单词 分隔开。

返回 单词 顺序颠倒且 单词 之间用单个空格连接的结果字符串。

注意:输入字符串 s中可能会存在前导空格、尾随空格或者单词间的多个空格。返回的结果字符串中,单词间应当仅用单个空格分隔,且不包含任何额外的空格。

示例 1:

输入:s = "the sky is blue"
输出:"blue is sky the"

示例 2:

输入:s = "  hello world  "
输出:"world hello"
解释:反转后的字符串中不能存在前导空格和尾随空格。

示例 3:

输入:s = "a good   example"
输出:"example good a"
解释:如果两个单词间有多余的空格,反转后的字符串需要将单词间的空格减少到仅有一个。

二、思路

        刚开始看这题就觉得挺难的。如果调用库函数还能解决,如果不调用库函数就有些麻烦。

        最终选择了一种比较容易理解的方法:先去除字符串多余的空格。再反转整个字符串,再反转各个单词。代码中有个人注释,希望能帮助到大家,欢迎指出理解错误的地方!

三、代码

       第一种方法:调用库函数

        针对split函数的解释:

        需要注意的是,split(" ") 会将连续的空格视为多个分隔符,并且会生成空字符串作为结果数组中的元素。这意味着如果输入字符串中有多个连续的空格,split(" ") 会生成一些空字符串。
例如,对于输入字符串 "a good example",使用 split(" ") 会得到以下数组: 

String[ ] str = {"a", "good", "", "", "example"};

所以加入了if判断。

class Solution {
    public String reverseWords(String s) {
        //用split函数分割出所有的单词
        String[] str = s.split(" ");
        StringBuilder sb = new StringBuilder();
        for (int i = str.length - 1; i >= 0; i--) {
            if (str[i].length() > 0) {
                sb.append(str[i]).append(" ");
            }
        }
        return sb.toString().trim(); //去除尾部的空格
    }
}

第二种方法:

class Solution {
    public String reverseWords(String s) {
        //1.先去除多余空格
        StringBuilder sb = removeSpace(s);
        //2.反转整个字符串
        reverse(sb,0,sb.length() - 1);
        //3.反转每个单词
        reverseWord(sb);
        return sb.toString();
    }
    public StringBuilder removeSpace(String s){
        //1.首先找到第一个字符和最后一个字符,去除首尾空格
        int start = 0;
        int end = s.length() - 1;
        while(s.charAt(start) == ' ') start++;
        while(s.charAt(end) == ' ') end--;
        //2.用StringBuilder拼接
        StringBuilder sb = new StringBuilder();
        while(start <= end) {  
            char c = s.charAt(start);
            //第二个条件需要理解,是为了不拼接连续的空格
            //当c为字母时,直接拼接,若c为空格,就需要考虑已经拼接的字符串
            //如果字符串末尾是空格,就不能拼接空格c,避免出现多个空格。
            //不是空格说明到达了一个单词的结尾,需加入空格
            if(c != ' ' || sb.charAt(sb.length() - 1) !=' ') {  
                sb.append(c);
            }
            start++;
        }
        return sb;
    }
    public void reverse(StringBuilder sb,int start, int end){
        //双指针进行反转,这里用到setCharAt函数,
        //或者直接调用reverse函数
        while(start <= end) {
            char temp = sb.charAt(start);
            sb.setCharAt(start,sb.charAt(end));
            sb.setCharAt(end,temp);
            start++;
            end--;
        }
    }
    public void reverseWord(StringBuilder sb){
        //反转单词
        int start = 0;
        int end = 1;
        int n = sb.length();
        while(start < n) {
             while (end < n && sb.charAt(end) != ' ') {   //找到单词的末尾后的空格
                end++;
            }
            reverse(sb, start, end - 1);   //反转该单词
            start = end + 1;  //跳过空格
            end = start + 1;    //找下一个单词
        }
    }
}
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值