嗨,陌生人,你好。欢迎来到令辰柒的博客主页!✨
🍛博主简介:一名大二即将升大三的科班学生,正在努力学习编程!
🍮系列专栏:【牛客刷题记录站】。(欢迎订阅)☕
🍎正文开始:
🍊问题要求:
实现一个函数,可以左旋字符串中的k个字符。
🚢例如:
ABCD左旋一个字符得到BCDA
ABCD左旋两个字符得到CDAB
🍵🍵问题分析:从给出的条件可以看出,我们需要给定我们的旋转次数,然后依次把字符串前面的元素经过旋转放到字符串后面去。
方法1
🍇直接了当法:
🍈第一种方法的思想就是我们把第一个字符用tmp单独存放起来,然后将整个字符串整体向前移动一位,最后我们把tmp里面存放的字符放到后面。
void leftRound(char * src, int time)
{
int i, j, tmp;
int len = strlen(src);
time %= len; //长度为5的情况下,旋转6、11、16...次相当于1次,7、12、17...次相当于2次,以此类推。
for (i = 0; i < time; i++) //执行k次的单次平移
{
tmp = src[0];
for(j = 0; j < len - 1; j++) //单次平移
{
src[j] = src[j + 1];
}
src[j] = tmp;
}
}
方法2
⛵拼接法:
void leftRound(char * src, int time)
{
int len = strlen(src);
int pos = time % len; //断开位置的下标
char tmp[256] = { 0 }; //更准确的话可以选择malloc len + 1个字节的空间来做这个tmp
strcpy(tmp, src + pos); //先将后面的全部拷过来
strncat(tmp, src, pos); //然后将前面几个接上
strcpy(src, tmp); //最后拷回去
}
方法3
🛸逆序法:
🛥️🛥️先将要左旋的前三个家伙逆序(CBADEFG),然后将后半段也逆序CBAGFED),最后整体逆序(DEFGABC)即可。这样只需要做数值交换即可,可以写一个函数帮我们完成局部逆序,代码如下:
void reverse_part(char *str, int start, int end) //将字符串从start到end这一段逆序
{
int i, j;
char tmp;
for (i = start, j = end; i < j; i++, j--)
{
tmp = str[i];
str[i] = str[j];
str[j] = tmp;
}
}
void leftRound(char * src, int time)
{
int len = strlen(src);
int pos = time % len;
reverse_part(src, 0, pos - 1); //逆序前段
reverse_part(src, pos, len - 1); //逆序后段
reverse_part(src, 0, len - 1); //整体逆序
}
🚈运行结果:
🛩️VS下完整代码:
#define _CRT_SECURE_NO_WARNINGS
#include<stdio.h>
void reverse_part(char* str, int start, int end) //将字符串从start到end这一段逆序
{
int i, j;
char tmp;
for (i = start, j = end; i < j; i++, j--)
{
tmp = str[i];
str[i] = str[j];
str[j] = tmp;
}
}
void leftRound(char* src, int time)
{
int len = strlen(src);
int pos = time % len;
reverse_part(src, 0, pos - 1); //逆序前段
reverse_part(src, pos, len - 1); //逆序后段
reverse_part(src, 0, len - 1); //整体逆序
printf("%s\n", src);
}
int main()
{
int a = 0;
scanf("%d", &a);
char arr[] = "abcdef";
leftRound(arr, 2);
return 0;
}