题目:翻转单词顺序
参考文献:
剑指offer 何海涛老师 P220
1.翻转整个句子
如 I am alex! ---> !xela am I
void reverseSentence(char *sen,int n){
int start=0;
// !int end1 = sizeof(sen)/sizeof(sen[0])-1;
// !printf("end1=%d\n",end1);
int end = n-1;
// printf("end=%d\n",end);
//不能用start<=n/2。
while(start <(n/2)){
//A^0 = A; A^1 = A的各位相反
//A^A=0 A=A^B B=B^A=B^A^B=A; A=A^B=A^B^A=B
sen[start] ^= sen[end];
sen[end] ^= sen[start];
sen[start] ^= sen[end];
start++;
end--;
}
}
2.翻转单词顺序
如I am alex! --> alex! am I 。其实只需要在1的基础上继续将每个单词顺序颠倒。
void reverseWordsInSentence(char *sen){
char *high,*low;
reverseSentence(sen,strlen(sen));
printf("sen转换后:\n");
puts(sen);
high = sen;
low = sen;
printf("word转换后:\n");
while(*high!='\0'){
//找到不是空格的字符即为单词的头。
while(*high==' ' && *high!='\0'){
high++;
}
low = high;
//找到空格的字符即为单词结尾的下一个字符
while(*high!=' ' && *high!='\0'){
high++;
}
//此时交换一个单词的首尾
reverseSentence(low,high-low);
puts(sen);
}
}
3.左旋转字符串。
如abceefg 左旋转2个字符得到ceefgab
void leftReverse(char *sen,int n){
char *high;
int len = n, i=0;
high = sen;
//添加边界值判断。当n==strlen(sen)不需要旋转 。当n<0也不需要旋转。当字符串为空,更不用旋转
if(strlen(sen) >0 && n>0 && n < strlen(sen)){
for(;i<n;i++){
high++;
}
reverseSentence(sen,len);
printf("%c,%d\n",*high,strlen(sen)-len);
reverseSentence(high,strlen(sen)-len);
reverseSentence(sen,strlen(sen));
}
}
下面给出c++实现的版本:
c++是string 操作有一些方法,如求长度 str.length(),对字符串的修改不会反映到字符串中,要保存结果可以用replace() 替换字符。
如 string s = "abcdefg"; s.replace(2,3,"!!!!!");//从索引2开始3个字节的字符全替换成"!!!!!"
string ReverseSentence(string str) {
int high,low;
str=reverseSentence(str,str.length());
cout<<"??"<<str<<"??"<<endl;
high = 0;
low = 0;
string temp;
while(str[high]!='\0'){
//找到不是空格的字符即为单词的头。
while(str[high]==' ' && str[high]!='\0'){
high++;
}
low = high;
//找到空格的字符即为单词结尾的下一个字符
while(str[high]!=' ' && str[high]!='\0'){
high++;
}
//此时交换一个单词的首尾
temp=reverseSentence(str.substr(low,str.length()),high-low);
cout<<"temp="<<temp<<endl;
str.replace(low,str.length(),temp);
}
return str;
}
string reverseSentence(string sen,int n){
int start=0;
// !int end1 = sizeof(sen)/sizeof(sen[0])-1;
// !printf("end1=%d\n",end1);
int end = n-1;
// printf("end=%d\n",end);
//不能用start<=n/2。
while(start <(n/2)){
//A^0 = A; A^1 = A的各位相反
//A^A=0 A=A^B B=B^A=B^A^B=A; A=A^B=A^B^A=B
sen[start] ^= sen[end];
sen[end] ^= sen[start];
sen[start] ^= sen[end];
start++;
end--;
}
return sen;
}
string leftReverse(string str, int n) {
int high;
int len = str.length(), i=0;
high = 0;
string temp,temp2;
//添加边界值判断。当n==strlen(sen)不需要旋转 。当n<0也不需要旋转。当字符串为空,更不用旋转
if(len>0 && n>0 && n < len){
for(;i<n;i++){
high++;
}
temp=reverseSentence(str,n);
cout<<"temp="<<temp<<endl;
str.replace(0,temp.length(),temp);
temp2=reverseSentence(str.substr(high,len),len-n);
str.replace(high,len,temp2);
str=reverseSentence(str,len);
}
return str;
}