我正在实现一种算法,当用户给出输入字符串时,字符串中的每个字符(如果是字母表)都应该增加给定的值(这里是旋转器)。我正在使用这段代码2小时,但无法弄清楚为什么当我按值旋转器增加时,它会被rotator-1增加。
public class Solution {
public static void main(String[] args) {
/* Enter your code here. Read input from STDIN. Print output to STDOUT. Your class should be named Solution. */
Scanner in = new Scanner(System.in);
int length = in.nextInt();
String input = in.next();
int nextvalue = 0;
int temp = 0;
char array[] = input.toCharArray();
int rotator = in.nextInt();
for(int i = 0; i < length; i++){
if((array[i] >= 'a' && array[i] <= 'z') || (array[i] >= 'A' && array[i] <= 'Z')){
nextvalue = (int)array[i] + rotator;
array[i] = (char)nextvalue;
if((int)array[i] > (int)'z'){
temp = (int)array[i] - (int)'z';
nextvalue = (int)'a' + temp -1;
array[i] = (char)nextvalue;
}
else if((int)array[i] > (int)'Z'){
temp = (int)array[i] - (int)'Z';
nextvalue = (int)'Z' + temp -1;
array[i] = (char)nextvalue;
}
}
}
System.out.println(array);
}
}
如果有两个if语句要处理(溢出条件),如果letter是&gt; z或&gt; Z.现在如果我删除那两个语句,除了溢出条件之外的所有内容都被正确打印
(没有溢出情况) 样本I / P:
11&lt; - String length
中等OUTZ
2&lt; - rotator
样本O / P:
okffng-Qwv |
&lt; - 未处理溢出情况
(有溢出情况) 样本I / P:
11
中等OUTZ
2
样本O / P:
njeemf-Qvu b
&lt; - 溢出处理,但其他一切由rotator增加 - 1除了&#39; Q&#39;
为什么会这样?我还在内部if条件中使用print语句进行检查,因为只有一个溢出条件,它只对该输入执行一次。
帮助/建议赞赏。谢谢。
答案 0 :(得分:3)
我认为处理溢出情况的最简单方法是使用模数运算符让字符环绕任意次,以便在当前逻辑位置着陆。这样的事情应该有效:
for (int i=0; i < length; i++) {
if (array[i] >= 'a' && array[i] <= 'z') {
int currDiff = (int)array[i] - (int)'a';
int newPos = (int)'a' + ((rotator + currDiff) % 26);
array[i] = (char)newPos;
}
else if (array[i] >= 'A' && array[i] <= 'Z') {
int currDiff = (int)array[i] - (int)'A';
int newPos = (int)'A' + ((rotator + currDiff) % 26);
array[i] = (char)newPos;
}
}
我使用输入字符串abcdefg
和rotator
值51来测试此代码,该值返回zabcdef
。这是预料之中的,因为我们只旋转了两个完整轮次。因此,a
在完成一次轮换后降落在z
,并且以下字符也会跟进。
请注意,这里处理字符位置微积分的方法要好得多,但这个答案仍然适用于你在原始问题中的处理方式。
最后说明:
模数运算符%
返回前面的数字除法的余数,继续它。在上面给出的解决方案中,我采用有效旋转器%26。这里,有效旋转器是字母与a
或A
加上的当前距离,但是很多我们想要旋转的步骤。通过取这个数字mod 26,我们总是会得到0到25之间的数字。因此,我们总是需要从a
或A
开始0到25步,这是你想要的行为在你的程序中。
答案 1 :(得分:2)
错误在于这一行:
if ((int) array[i] > (int) 'Z') {
你必须记住小写字母是“大写字母后”:'Z'用90表示,(例如)'j'用106表示(更多信息请参见this) 。 'Q'不受此错误影响的原因是因为它也是一个大写字母,因此具有比'Z'更小的十进制表示。
要解决此问题,您必须使用以下内容替换上面的代码行:
if ((int) array[i] > (int) 'Z' && (int) array[i] <= (int) 'Z' + rotator) {
答案 2 :(得分:2)
因为你在循环中修改它两次。
for(int i = 0; i < length; i++){
if((array[i] >= 'a' && array[i] <= 'z') || (array[i] >= 'A' && array[i] <= 'Z')){
nextvalue = (int)array[i] + rotator;
array[i] = (char)nextvalue; //<-- modifies from m to o
if((int)array[i] > (int)'z'){
temp = (int)array[i] - (int)'z';
nextvalue = (int)'a' + temp -1;
array[i] = (char)nextvalue;
}
else if((int)array[i] > (int)'Z'){
temp = (int)array[i] - (int)'Z';
nextvalue = (int)'Z' + temp -1;
array[i] = (char)nextvalue; //<--modifies again from o to n
}
}
}
答案 3 :(得分:1)
而不是
nextvalue = (int)'Z' + temp -1;
不应该是
nextvalue = (int)'A' + temp -1;