问题一:左旋转字符串
题目描述
汇编语言中有一种移位指令叫做循环左移(ROL),现在有个简单的任务,就是用字符串模拟这个指令的运算结果。对于一个给定的字符序列S,请你把其循环左移K位后的序列输出。例如,字符序列S=”abcXYZdef”,要求输出循环左移3位后的结果,即“XYZdefabc”。是不是很简单?OK,搞定它!
解题思路
如果没有看《剑指》,自己的思路可能还是停留在字符的移位上。
这个思路就是翻转再翻转:如果左移n位,就先将前n个翻转,再将后边的翻转,再将整体翻转。
以”abcXYZdef”,n=3为例:
Step1:前3个旋转 ,得到 cbaXYZdef
Step2:后边旋转,得到 cbafedZYX
Step3:整体再旋转,得到XYZdefabc
实现了左移的效果。
写代码时候,注意步骤之间的联系,三步都用到了旋转代码,所以可以只写一个函数,然后传入选择字符串的前后下标
题解
public String LeftRotateString(String str,int n) {
if(str == null) return null;
int len = str.length();
char[] arr = str.toCharArray();
reverse(arr,0,n-1);
reverse(arr,n,len-1);
reverse(arr,0,len-1);
// char[] 转 String的一种方法 String.valueOf
String result = String.copyValueOf(arr);
return result;
}
public void reverse(char[] arr,int i,int j){
while(i < j){
char temp = arr[i];
arr[i] = arr[j];
arr[j] = temp;
i++;
j--;
}
}
问题二:翻转单词序列
题目描述
牛客最近来了一个新员工Fish,每天早晨总是会拿着一本英文杂志,写些句子在本子上。同事Cat对Fish写的内容颇感兴趣,有一天他向Fish借来翻看,但却读不懂它的意思。例如,“student. a am I”。后来才意识到,这家伙原来把句子单词的顺序翻转了,正确的句子应该是“I am a student.”。Cat对一一的翻转这些单词顺序可不在行,你能帮助他么?
解题思路
输入“I am a student.”输出“student. a am I”
句子颠倒,但是保证单词内容不颠倒。相同的思想,可以整体翻转,然后再将每个单词内部翻转即可
以本题举例说明
Step1:整句翻转,得到“.tneduts a ma I”
Step2:对单词逐个翻转。
翻转第一个 “student. a ma I”
翻转第二个 "student. a ma I"
翻转第三个 "student. a am I"
翻转第四个 “student. a am I”
其实单个单词就不用翻转了。
题解
public String ReverseSentence(String str) {
int n = str.length();
if(n <= 0) return str;
char[] arr = str.toCharArray();
reverse(arr,0,n-1);
int i = 0,j=0;
while(i < n ){
if (j == n){
reverse(arr,i,j-1);
break;
}
else if (arr[j] == ' ' || arr[j] == '\n'){
reverse(arr,i,j-1);
i = j+1;
j = i;
}
else {
j++;
}
}
// char[] 转String 的另一种方法
return new String(arr);
}
public void reverse(char[] str,int lo,int hi){
while(lo < hi) {
char temp = str[lo];
str[lo] = str[hi];
str[hi] = temp;
lo++;
hi--;
}
}