/*
反转单词顺序:
输入一个英文句子,反转句子中单词的顺序,但单词内字符的顺序不变,为了简单起见,标点符号和普通字母
一样处理。例如输入字符串"I am a student.",则输出"student. a am I"。
思路:
首先将整个字符串完全反转,然后对单个单词利用空格做切分后反转
输入:
每个测试案例为一行,表示一句英文句子。
我们保证一个句子的单词数不会超过600,每个单词的长度也不会超过30。但是需要注意的是Fish是个不拘小节的人,有时候两个单词中间可能会有很多空格。为了方便起见,你可以认为一行的字符总数不会超过50000个,标点符号可以和普通字母一样处理。
输出:
对应每个测试案例,把翻转后的正确的句子单独输出一行。
样例输入:
student. a am I
I'm a Freshman and I like JOBDU!
样例输出:
I am a student.
JOBDU! like I and Freshman a I'm
*/
/*
关键:
1 首先将整个字符串完全反转,然后对单个单词利用空格做切分后反转
2 while(*pEnd != '\0')
{
pEnd++;
}
--pEnd;//注意这里必须要用pEnd指向最后一个字符,因此需要减减
3 pBeg = pEnd = str;//注意,这里用给pBeg和pEnd重新赋值,否则沿用上次计算的值就会出错
4 if(*pBeg == ' ')//如果遇到空格,就令起点指针和末尾指针,均开始累加
{
pBeg++;
pEnd++;
}
5 else if(*pEnd == ' ' || *pEnd == '\0')//如果末尾指针走到下一个空白处或者字符末尾,那么,就可以反转单词了
{
reverseStr(pBeg,--pEnd);//牛逼,这里注意将pEnd向前遍历,确保是单词的最后一个字符
pBeg = ++pEnd;//牛逼,这里实际上让pBeg和pEnd同步了,并且都指向空白字符处
6 else//其余普通情况,只需要累加末尾指针
{
pEnd++;
}
*/
#include <stdio.h>
#include <string.h>
const int MAXSIZE = 1e4 + 1;
void reverseStr(char* sBeg,char* sEnd)
{
if(!sBeg || !sEnd)
{
return;
}
char ch;
while(sBeg < sEnd)//交换两个字符,注意这里是sBeg < sEnd,而不是sBeg != sEnd
{
ch = *sBeg;
*sBeg = *sEnd;
*sEnd = ch;
sBeg++;
sEnd--;
}
}
char* reverseSentence(char* str)
{
char* pBeg = str,*pEnd = str;
int iIndex = 0 ;
while(*pEnd != '\0')
{
pEnd++;
}
--pEnd;//注意这里必须要用pEnd指向最后一个字符,因此需要减减
//反转整个句子
reverseStr(pBeg,pEnd);
pBeg = pEnd = str;//注意,这里用给pBeg和pEnd重新赋值,否则沿用上次计算的值就会出错
//printf("%s\n",str);
while(*pBeg != '\0')//开始对每个句子中的每个单词进行反转
{
if(*pBeg == ' ')//如果遇到空格,就令起点指针和末尾指针,均开始累加
{
pBeg++;
pEnd++;
}
else if(*pEnd == ' ' || *pEnd == '\0')//如果末尾指针走到下一个空白处或者字符末尾,那么,就可以反转单词了
{
reverseStr(pBeg,--pEnd);//牛逼,这里注意将pEnd向前遍历,确保是单词的最后一个字符
pBeg = ++pEnd;//牛逼,这里实际上让pBeg和pEnd同步了,并且都指向空白字符处
}
else//其余普通情况,只需要累加末尾指针
{
pEnd++;
}
}
return str;
}
//注意:反转整个句子,我们的思路是找到当前空白字符的下一个字符,以及下一个空白字符的前一个字符,然后
//把这段进行反转
void process()
{
char str[MAXSIZE];
while(NULL != gets(str))
{
printf("%s\n",reverseSentence(str));
}
}
int main(int argc,char* argv[])
{
process();
getchar();
return 0;
}