1 题目
题目:旋转字符串(Rotate String)
描述:给定一个字符串str和一个偏移量,根据偏移量原地旋转字符串(从左向右旋转)。
- offset >= 0
- str的长度 >= 0
- 原地旋转意味着需要在函数中更改字符串s。你不需要返回任何东西。
lintcode题号——8,难度——easy
样例1:
输入:
str = "abcdefg"
offset = 3
输出:"efgabcd"
解释:注意是原地旋转,即str旋转后为"efgabcd"
样例2:
输入:
str = "abcdefg"
offset = 0
输出:"abcdefg"
解释:注意是原地旋转,即str旋转后为"abcdefg"
样例 3:
输入:
str = "abcdefg"
offset = 10
输出:"efgabcd"
解释:注意是原地旋转,即str旋转后为"efgabcd"
2 解决方案
2.1 思路
对于旋转排序数组,经常使用的操作是三步翻转法,找到中间位置,翻转左右区间,再翻转整个序列即可完成对数组的构造,该方式是可逆的,也可以用来恢复旋转排序数组。
每次翻转如果不使用库函数,可以使用双指针算法自己写。
2.2 时间复杂度
翻转操作需要遍历整个序列,时间复杂度为O(n)。
2.3 空间复杂度
空间复杂度为O(1)。
3 源码
细节:
- 使用三步翻转法,找到中间位置,翻转左右区间,再翻转整个序列即可。
- 取size时候需要转成int型再计算,否则容易出错,因为size_t类型不能为负。
- 如果翻转不用reverse函数的话,需要对向双指针来实现reverse函数的功能。
C++版本:
/**
* @param s: An array of char
* @param offset: An integer
* @return: nothing
*/
void rotateString(vector<char> &s, int offset) {
// write your code here
if (s.empty() || offset == 0)
{
return;
}
int mid = (int)s.size() - offset % (int)s.size();
reverse(s.begin(), s.begin() + mid); // 直接使用翻转函数
reverse(s.begin() + mid, s.end());
reverse(s.begin(), s.end());
}