https://leetcode-cn.com/problems/he-wei-sde-lian-xu-zheng-shu-xu-lie-lcof/
题目描述
输入一个正整数 target ,输出所有和为 target 的连续正整数序列(至少含有两个数)。
序列内的数字由小到大排列,不同序列按照首个数字从小到大排列。
输入输出样例
示例 1:
输入:target = 9
输出:[[2,3,4],[4,5]]
示例 2:
输入:target = 15
输出:[[1,2,3,4,5],[4,5,6],[7,8]]
滑动窗口法
class Solution {
public int[][] findContinuousSequence(int target) {
// 使用滑动窗口解题,由于是连续的正整数序列,所以左右窗口的起点都是1
int l = 1;
int r = 1;
int sum = 0;
ArrayList<int[]> list = new ArrayList<>();
// 循环条件需要选好
while(l <= target/2){
if(sum > target){
sum -= l;
l++;
}
else if(sum < target){
sum += r;
r++;
}
else{ // sum == target
int[] temp = new int[r-l];
for(int i=l; i<r; i++){
temp[i-l] = i;
}
list.add(temp);
sum -= l;
l++;
}
}
// 返回值的时候需要注意如何产生 int[][]
return list.toArray(new int[list.size()][]);
}
}
找规律大法
class Solution {
public int[][] findContinuousSequence(int target) {
// 核心算法参考 https://leetcode-cn.com/problems/consecutive-numbers-sum/solution/c-ji-jian-by-pris_bupt/
// 举例
// 7 * 2 + 1 = 15
// 4 * 3 + 1 + 2 = 15
// 1 * 5 + 1 + 2 + 3 + 4 = 15
// 即
// 7 * 2 = 15 - 1
// 4 * 3 = 15 - 1 - 2
// 1 * 5 = 15 - 1 - 2 - 3 - 4
// 按此规则写出如下算法
List<int[]> list = new ArrayList<>();
for (int i = 1; target > 0; i++) {
if (i != 1 && target % i == 0) { // 如果可以整除,说明可以组成连续正数序列
// 需要把1排除,因为本题target自身不算是连续正数序列
int start = target / i; // 获取连续序列的第一个数
int[] nums = new int[i]; // 连续序列共有i个数
for (int j = 0; j < i; j++) {
nums[j] = start + j;
}
list.add(nums);
}
target -= i;
}
int[][] result = new int[list.size()][];
for (int i = result.length - 1; i >= 0; i--) {
result[result.length - 1 - i] = list.get(i);
}
return result;
}
}