(方法3只给出思路参考)
问题
描述:
实现一个函数,可以左旋字符串中的k个字符。
例如:
ABCD左旋一个字符得到BCDA
ABCD左旋两个字符得到CDAB
分析
我们先来理解一下,什么叫“左旋”?其实是这个意思:
由于没有规定左旋次数限制,我们还要注意的是,左旋4次后又变回原来的字符顺序了。所以左旋5次相当于左旋1次。(这样可以优化我们的代码)
在搞清楚这点后,我们才应该开始想具体的左旋代码怎么写。
方法1
我们一次旋一个,把旋几个当成旋几次。
那么现在旋一次要怎么写呢?
首先,我们创建一个临时变量,把第一个字符赋给它;
其次,让后面的字符依次向前移动一位;
最后,把临时变量的字符赋给字符串的最后一个位置。
参考代码:
#include<stdio.h>
#include<string.h>
void zuo(char str[],int num)
{
int len = strlen(str);
num = num % len;//优化
//假如ABCD旋5次,就变为旋5%4即1次
while (num--)//旋num次
{
//我们就不要左旋几个一次操作几个了,而是当作次数。每次就旋一个。
char tmp = str[0];
//把后一个赋前一个,就可以实现往前移
int i = 0;
while (i < len - 1)//如果是len,i最大取值len-1,但是i+1取到len,str[len]越界了
{
str[i] = str[i + 1];
i++;
}
//此时i为len-1,str[i]为最后一个字符
str[i] = tmp;//注意不要错写成str[i+1]=tmp;
}
}
int main()
{
char str[50];
scanf("%s", str);
int num;
scanf("%d", &num);//把要旋的次数传过去
zuo(str,num);
printf("%s\n", str);
return 0;
}
(提示:printf() 输出字符串时,会从第 0 个元素开始往后检索,直到遇见’\0’才停止,然后把’\0’前面的字符全部输出,这就是 printf() 输出字符串的原理。)
运行效果:
方法2
使用strcpy和strncat
现在我们就不将旋几个看为旋几次了,而是直接要旋几个就一次性旋几个,而要达到这一效果我们就不得不使用到函数strcpy和strcat。
实现逻辑就是我们创建一个临时数组:char tmp[50];把左旋字符以外的后面的字符先拷贝进tmp,再将要左旋的字符拼接到tmp后面,此时得到的tmp就是左旋后的字符数组,我们再将其拷贝回str。
那么在写代码前先来关心一下我们的strcpy和strcat:
前一个参数是目标地址,后一个参数是源地址。也就是说前一个参数是指向我们要拷贝到的字符数组,后一个参数被拷贝的字符串。
strcat的参数看起来和strcpy一样,前一个也是char* destination 后一个也是char* source,但前一个参数指向的是要被拼接的字符数组,后一个参数指向的是拼接物。
(图示)
但是我们会注意到strcat会把作为source的字符串整个拼接到destination,而对于本题目而言,我们只想拼接我们左旋个数的字符,假如我们要对ABCD左旋2个,在把字符CD拷贝进tmp之后我们需要再将AB拼接到tmp后面,如果写的是strcat(tmp,str);那么会变成CDABCD:
所以我们应该使用的是strncat函数,可以按我们拼接我们想要的个数。
区别就是,strncat(tmp,str,num);会将str开始的num个字符拼接到tmp的末尾处。
了解怎么调用后,我们就可以写我们的代码了:
这就是我们的方法2。
方法3
到此,本文就结束了,祝阅读愉快^_^