题目详情
给你一个按升序排序的整数数组num(可能包含重复数字),请你将它们分割成一个或多个长度至少为3的子序列,其中每个子序列都由连续整数组成。如果可完成上述分割,则返回true;否则,返回false。
示例1
输入:{1, 2, 3, 4, 5}
输出:True
解释:
你可以分割出这样两个连续子序列:
1, 2, 3
3, 4, 5
示例2:
输入:{1, 2, 3, 3, 4, 4, 5, 5}
输出:True
解释:
你可以分割出这样两个连续子序列:
1, 2, 3, 4, 5
3, 4, 5
示例3:
输入:{1, 2, 3, 4, 4, 5}
输出:False
思路:
因为数组为升序数组,且子序列需要连续整数,可以将数组转换为统计关键字数量数组,使用统计数组进行排列。
分割数组不要求计算可分割数量,故而时将子序列按最大长度分割,当元素为最后一种元素或元素统计数比下一个元
素统计数大的时候分割
实现:
public static boolean subSequence(int[] array) {
// 子序列最小长度
int standard = 3;
// 原数组不达到子序列最小长度
if (array.length < standard) {
return false;
}
// 统计数组 长度为array.length 防止数组下标上限越界
int[] copy = new int[array.length];
// 统计
for (int i : array) {
copy[i - array[0]]++;
}
// 获取最后一个非0数字 copy初始化的时候所有元素为0
int lastIndex = copy.length - 1;
while (copy[lastIndex] == 0) {
lastIndex--;
}
// 元素种数不达到子序列最小长度
if (lastIndex < standard - 1) {
return false;
}
// 判断元素是否为连续不间断
for (int i = 0; i <= lastIndex; i++) {
if (copy[i] == 0) {
return false;
}
}
// first为每一个子序列起始位置,count为子序列长度
int first = 0, count;
// 辅助变量,判断下一个子序列起始位置是否找到
boolean flag;
// 因为后续每一次子序列获取元素时,统计数组对应元素的统计数会减-,所以最后一个元素统计数为0时数组分割完成
while (copy[lastIndex] != 0) {
count = 0;
flag = false;
// 从子序列起始位置找到所有子序列元素
for (int i = first; i <= lastIndex; i++) {
// 数量不为1 下一个子序列起始位置则是这个一个元素
if (copy[i] != 1 && !flag) {
flag = true;
first = i;
}
// 子序列数量+1
count++;
copy[i]--;
// 当元素为最后一种元素或元素统计数比下一个元素统计数大(=是因为之前已经-1,所以存在=的情况)的时候完成分割
if (i != lastIndex && copy[i] >= copy[i + 1]) {
break;
}
}
// 判断是否符合数量要求
if (count < standard) {
return false;
}
}
return true;
}
验证:
public static void main(String[] args) {
System.out.println(subSequence(new int[]{1, 2, 3, 3, 4, 5}));
System.out.println(subSequence(new int[]{}));
System.out.println(subSequence(new int[]{1, 2, 3, 3, 4, 4, 5, 5}));
System.out.println(subSequence(new int[]{1, 2, 3, 4, 4, 5}));
System.out.println(subSequence(new int[]{1, 2, 3, 3, 4, 4, 5}));
System.out.println(subSequence(new int[]{1, 2, 3, 3, 4, 4, 4, 5, 5, 6}));
System.out.println(subSequence(new int[]{1, 2, 3, 3, 4, 4, 4, 4, 5, 5, 5, 6, 6}));
}
结果:
true
false
true
false
true
true
true