《剑指offer》73--翻转单词序列[C++][Java]

这篇博客主要介绍了如何解决编程问题中的一种常见挑战:翻转字符串中的单词顺序。作者提供了多种C++实现方法,包括字符头插拼接、使用栈以及分段翻转,并对比了不同解法的效率。此外,还提到了Java的解决方案,通过字符串切分实现单词顺序的反转。这些方法对于理解和提高字符串处理技巧非常有帮助。
摘要由CSDN通过智能技术生成

翻转单词序列_牛客题霸_牛客网【牛客题霸】收集各企业高频校招笔面试题目,配有官方题解,在线进行百度阿里腾讯网易等互联网名企笔试面试模拟考试练习,和牛人一起讨论经典试题,全面提升你的技术能力https://www.nowcoder.com/practice/3194a4f4cf814f63919d0790578d51f3?tpId=13&tqId=11197&tPage=1&rp=1&ru=/ta/coding-interviews&qru=/ta/coding-interviews/question-ranking

题目描述

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

解题思路

【C++解法】

1、字符头插拼接

class Solution {
public:
    string ReverseSentence(string str) {
        string res = "";
        string tmp = "";
        for (int i = 0; i < str.length(); i++) {
            if (str[i] == ' ') { //注意此处为单引号
                res = " " + tmp + res;
                tmp = "";
            } else {tmp += str[i];}
        }
        if (tmp.size()) {res = tmp + res;}
        return res;
    }
};

2、栈

class Solution {
public:
    string ReverseSentence(string str) {
        stack<string> Words;
        int BlankPos = 0, perPos = 0;
        string subString;
        while (BlankPos >= 0) {
            BlankPos = str.find_first_of(' ', perPos); //找到空格分隔字符串
            Words.push(str.substr(perPos, (BlankPos < 0) //把单词压如栈
                                  ? (str.length() - perPos)
                                  : (BlankPos - perPos))); //按长度截取单词
            perPos = BlankPos + 1;
        }
        subString.clear();
        while (!Words.empty()) {
            subString += Words.top();
            Words.pop();
            if(!Words.empty()) {subString += " ";} //需不需要加空格
        }
        return subString;
    }
};

3、分段翻转

两次翻转,第一次整体翻转,第二次每个单词再翻转,也可以反过来。时间O(n),空间O(1) 。

自定义revers:

class Solution {
public:
   void Reverse(string &s,int start,int end) {
        char temp;
        while(start<end) {
            temp=s[start];
            s[start]=s[end];
            s[end]=temp;
            start++;
            end--;
        }
    }
    string ReverseSentence(string str) {
        int len = str.length();
        if(!len) return str;
        string temp = str;
        Reverse(temp, 0, len-1);
        int begin = 0, end = 0;
        while(temp[begin] != '\0') {
            if(temp[begin] == ' ') {
                begin++;
                end++;
            } else if(temp[end] == ' ' || temp[end] == '\0') {
                Reverse(temp, begin, --end);
                begin = ++end;
            } else end++;
        }
        return temp;
    }
};

C++库里的reverse

class Solution {
public:
    string ReverseSentence(string str) {
        reverse(str.begin(), str.end());
        string::size_type s = 0, e;
        while((e=str.find(' ', s)) != string::npos){
            reverse(str.begin()+s, str.begin()+e);
            s = e + 1;
        }
        reverse(str.begin()+s, str.end());
        return str;
    }
};

使用swap

class Solution {
public:
    string ReverseSentence(string str) {
        auto size = str.size();
        if(size == 0) return "";
        int mark=0;
        str += ' ';
        for(int i = 0; i < size+1; ++i) {
            if(str[i] == ' ') {
                for(int l=mark,r=i-1;l<r;l++,r--) swap(str[l],str[r]);
                mark = i+1;
            }
        }
        str = str.substr(0, size);
        for(int l=0,r=size-1;l<r;l++,r--) swap(str[l],str[r]);
        return str;
    }
};

【Java解法】

public class Solution {
    public String ReverseSentence(String str) {
        String[] word = str.split(" ");
        String res = "";
        for (int i = word.length - 1; i >= 0; i--) {res += " " + word[i];}
        return res.substring(1);
    }
}

或者

public class Solution {
    public String ReverseSentence(String str) {
        String[] arr = str.split(" "); //与C++不同,Java这里需用双引号
        String res = arr[arr.length-1];
        for (int i=arr.length-2; i>=0; i--) {
            res += ' ' + arr[i];
        }
        return res;
    }
}

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

打赏作者

贫道绝缘子

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

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

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

打赏作者

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

抵扣说明:

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

余额充值