和为s的连续正数序列java_Java 实现和为S的连续正数序列

输出所有和为S的连续正数序列。

序列内按照从小至大的顺序,序列间按照开始数字从小到大的顺序(小明很喜欢数学,有一天他在做数学作业时,要求计算出9~16的和,他马上就写出了正确答案是100。但是他并不满足于此,他在想究竟有多少种连续的正数序列的和为100(至少包括两个数)。没多久,他就得到另一组连续正数和为100的序列:18,19,20,21,22。现在把问题交给你,你能不能也很快的找出所有和为S的连续正数序列?Good Luck!)

代码

public static List> findContinuesSequence(int target) {

// 至少包含两个数,所以最小也得是3,这样还有{1,2}一个组合满足

if (target < 3) {

return null;

}

// 初始化两个指针

int small = 1;

int big = 2;

// 获取目标值的一半

int middle = (target + 1) / 2;

// 保存结果

List> result = Lists.newArrayList();

// small < middel,因为big比small大,超过middle,small+big > target

// 等于也不可以,small+big>target

// 比如14,middel=7,如果small=7,big > small,small+big > target

// 所以所有结果的起始点应该在middle的左侧

int sum = small + big;

while (small < middle) {

/* 这是自己的写法

int sum = 0;

for (int i = small; i <= big; i++) {

sum += i;

}

if (sum == target) {

result.add(Lists.newArrayList(small, big));

big++;

} else if (sum > target) {

small++;

} else {

big++;

}

*/

// 如果和大于target,则减去较小的值small, 并移动small的指针,使得sum <= target

// sum <= target时,终结此次while

// sum > target时,减小范围,移动small的指针,此时需要减去大于target的部分

// sum = target时,记录此次结果,并且移动big的指针,扩大查找范围

// sum < target时,扩大范围,移动big的指针,此时需要更大的值来弥补和target的差距

// 比如 target = 15, small=1, big = 2

// sum = 1+2 =3, sum < target, small=1, big = 3

// sum = 1+2+3 = 6, sum < target, small=1, big = 4

// sum = 1+2+3+4 = 10, sum < target, small=1, big = 5

// sum = 1+2+3+4+5 = 15, sum = target, 找到, 扩大搜索范围, small=1, big = 6

// sum = 1+2+3+4+5+6 = 21, sum > target, small=2, big = 6

// sum = 2+3+4+5+6 = 20, sum > target, small=3, big = 6

// sum = 3+4+5+6 = 18, sum > target, small=4, big = 6

// sum = 4+5+6 = 15, sum = target, , 找到, 扩大搜索范围, small=4, big = 7

// sum = 4+5+6+7 = 22, sum > target, small=5, big = 7

// sum = 5+6+7 = 18, sum > target, small=6, big = 7

// sum = 6+7 = 13, sum < target, small=6, big = 8

// sum = 6+7+8 = 21, sum > target, small=7, big = 8

// sum = 7+8 = 15, sum = target, , 找到, 扩大搜索范围, small=7, big = 9

// sum = 7+8+9 = 24, sum > target, small=8, big = 9

// middel = (15 + 1) / 2 = 8, 不满足small < middle,退出

while (sum > target && small < middle) {

sum -= small;

small++;

if (sum == target) {

result.add(Lists.newArrayList(small, big));

}

}

big++;

sum += big;

}

return result;

}

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值