剑指offer:翻转单词顺序列

本文介绍了一种常见的字符串处理问题——句子单词顺序翻转的两种解决思路。第一种使用split方法将字符串转换为数组并倒序;第二种采用两次翻转策略,先整体翻转再单独翻转单词,适用于面试场景。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

题目描述

牛客最近来了一个新员工Fish,每天早晨总是会拿着一本英文杂志,写些句子在本子上。同事Cat对Fish写的内容颇感兴趣,有一天他向Fish借来翻看,但却读不懂它的意思。例如,“student. a am I”。后来才意识到,这家伙原来把句子单词的顺序翻转了,正确的句子应该是“I am a student.”。Cat对一一的翻转这些单词顺序可不在行,你能帮助他么?

思路1:

以单词为单位,通过split,将字符串转换为数组,倒序遍历数组,并将数组中的值放入Stringbuffer中并加上空格。

public class Solution {
    public String ReverseSentence(String str) {
        if(str.trim().length()==0){
            return str;
        }
        String[] strs=str.split(" ");
        StringBuffer sb=new StringBuffer();
        for(int i=strs.length-1;i>=0;i--){
            sb.append(strs[i]);
            if(i>0){
                sb.append(" ");
            }
        }
        return sb.toString();     
    }
}

当然,这种方法并不是面试官期望的方法。

 

思路2:

这类题的通用解法就是按照字符翻转,进行两次翻转。https://blog.youkuaiyun.com/orangefly0214/article/details/87267982左旋转字符串,这道题也是一样的方法。

step1:将整个句子先进行一次翻转。

step2:针对句子内部的每个单词,以空格为分隔符,进行 第二次翻转。

实现1:用两个指针,来得到单词的首尾部分

public class Solution {
    public String ReverseSentence(String str) {
        if(str.trim().length()==0){
            return str;
        }
        char[] strs=str.toCharArray();
        //首先反转整个句子
        reverse(strs,0,strs.length-1);
        //然后依次反转句子中的每个单词
        int begin=0;
        int end=0;
        while(begin<strs.length){
            if(strs[begin]==' '){
                begin++;
                end++;
            }else if(strs[end]==' '){//若遍历到终止字符为空,则进行翻转
                reverse(strs,begin,--end);
                begin=++end;
            }else if(end==strs.length-1){
                reverse(strs,begin,end);//若遍历结束,则对最后一个字符进行翻转
                begin=++end;
            }
            else{
                end++;
            }
        }
        return String.valueOf(strs);
    }
    private void reverse(char[] strs,int begin,int end){
        while(begin<end){
            char temp=strs[begin];
            strs[begin]=strs[end];
            strs[end]=temp;
            begin++;
            end--;
        }
    }
}

 

实现2:以空格为区分单词的标识

public class Solution {
    public String ReverseSentence(String str) {
        //通过空格来分隔句子中的单词
        if(str.trim().length()==0){
            return str;
        }
        char[] strs=str.toCharArray();
        //对句子进行整体翻转
        reverse(strs,0,strs.length-1);
        //翻转句子中的每个单词
        int blank=-1;
        for(int i=0;i<strs.length;i++){
            if(strs[i]==' '){
                int nextBlank=i;
                reverse(strs,blank+1,nextBlank-1);
                blank=nextBlank;
            }
        }
        reverse(strs,blank+1,strs.length-1);
        return new String(strs);       
    }
    private void reverse(char[] strs, int begin, int end) {
        while(begin<end){
            char temp=strs[begin];
            strs[begin]=strs[end];
            strs[end]=temp;
            begin++;
            end--;
        }
    }
}

 

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值