Java 递归-布尔条件和字符数组
我在这个递归练习中遇到了一个问题 练习是测试字符数组是否只有大写或小写,然后才返回true;否则,如果同时存在小写和大写字母,则返回false 下面的代码总是返回true 我试着在每次有大信号或小信号时都计算一个变量,然后如果数量等于数组,那么它是真的,否则它不是真的;但它没有给我这个。这是一个布尔函数,调用递归并没有给出变量的数量 守则:Java 递归-布尔条件和字符数组,java,recursion,Java,Recursion,我在这个递归练习中遇到了一个问题 练习是测试字符数组是否只有大写或小写,然后才返回true;否则,如果同时存在小写和大写字母,则返回false 下面的代码总是返回true 我试着在每次有大信号或小信号时都计算一个变量,然后如果数量等于数组,那么它是真的,否则它不是真的;但它没有给我这个。这是一个布尔函数,调用递归并没有给出变量的数量 守则: public static boolean Arr(char[] arr, int length) { if (length == -1)
public static boolean Arr(char[] arr, int length) {
if (length == -1)
return true;
boolean flag = Character.isUpperCase(arr[length]);
if (flag)
return true;
return Arr(arr, length - 1);
}
您需要函数中的附加参数和附加退出条件:
- 附加参数:上次读取的字符为小写或大写
- 要退出的附加测试:如果当前字符与最后一个字符的退出情况不同,则返回false
第二种方法不是从第一个字符开始,而是从第二个字符开始,检查当前字符和前一个字符之间的大小写是否相同。看看这是否有效
public static boolean Arr(char[] arr, int length) {
if (length == -1)
return true;
boolean flag = Character.isUpperCase(arr[length]);
if (flag)
return Arr(arr, length - 1);
else
return false;
}
这能满足你的需要吗
public
前端只接受一个字符数组,并使用终端用户不必担心的参数的起始值调用private
后端
public static boolean sameCase(char[] ary) {
return sameCase(ary, 0, ary.length - 1);
}
后端试图将阵列的当前段分成两个子段,将问题减半,使堆栈的增长率保持为O(log#chars)
,而不是O(#chars)
。如果当前段少于两个字符,则所有字符的大小写基本相同。否则,请检查每个子段是否具有大小写相同的字符,如果是,请使用XOR和技巧检查两个子段的大小写是否相同
private static boolean sameCase(char [] ary, int first, int last) {
int len = last - first + 1;
int mid = first + len / 2;
return len < 2 ||
(sameCase(ary, first, mid - 1) && sameCase(ary, mid, last) &&
(Character.isUpperCase(ary[first]) ^ Character.isLowerCase(ary[last])));
}
private静态布尔sameCase(char[]ary,int first,int last){
int len=最后一个-第一个+1;
int mid=第一个+长度/2;
返回长度<2||
(sameCase(ary,first,mid-1)和sameCase(ary,mid,last)&&
(Character.isUpperCase(ari[第一个])^ Character.isLowerCase(ari[最后一个]));
}
注意,通过对递归调用进行ANDing,逻辑短路平均加快了速度。在处理布尔代数时,编写一些单元来帮助我们验证我们的工作总是值得的:
import static org.junit.Assert.*;
import org.junit.Test;
public class CharactersSpec {
@Test
public void itShouldBeTrueWhenAllCharsAreUppercase() {
String input = "HELLO";
assertEquals(true, Characters.isSameCase(input.toCharArray()));
}
@Test
public void itShouldBeTrueWhenAllCharsAreLowercase() {
String input = "hello";
assertEquals(true, Characters.isSameCase(input.toCharArray()));
}
@Test
public void itShouldBeFalseWhenOneCharIsLowercase() {
String input = "HeLLO";
assertEquals(false, Characters.isSameCase(input.toCharArray()));
}
@Test
public void itShouldBeFalseWhenOneCharIsUppercase() {
String input = "hEllo";
assertEquals(false, Characters.isSameCase(input.toCharArray()));
}
}
然后可以实现该方法。我不会用递归实现它,但这似乎是您的任务的要求:
import java.util.Arrays;
public final class Characters {
public static boolean isSameCase(char[] chars) {
return isSameCase(chars, false, false);
}
private static boolean isSameCase(char[] chars, boolean uppercaseFound, boolean lowercaseFound) {
if(chars.length == 0) {
return true;
}
lowercaseFound |= Character.isLowerCase(chars[0]);
uppercaseFound |= Character.isUpperCase(chars[0]);
return !(lowercaseFound && uppercaseFound) && isSameCase(Arrays.copyOfRange(chars, 1, chars.length),
uppercaseFound,
lowercaseFound);
}
}
请注意以下几点:
- only
方法仅将public
作为参数,因此调用方不必担心递归细节char[]
- 我决定使用子数组而不是传递索引,这样方法签名就保留了3个参数(首先,我总是培养可读性而不是性能)
public static boolean isSameCase(String input) {
return input.equals(input.toLowerCase()) || input.equals(input.toUpperCase());
}
请注意:
- 我更喜欢在Java中操作
而不是String
(更方便)char[]
- 我会尽可能避免递归,因为我认为这种做法在Java中不太合适(大多数程序员不熟悉,该语言提供了其他循环方式)