如何获得所有连续数字组合形成一个数字?

v_a*_*_ag 6 java algorithm math loops

我想创建一个程序,生成连续数字组合,形成一个数字.例如.如果输入的数字是15,它应该给 -

7, 8
4, 5, 6
1, 2, 3, 4, 5
Run Code Online (Sandbox Code Playgroud)

一些公式/算法/循环可以做适合的事情.它可以生成一个数组或打印它.这似乎是一个数学问题或愚蠢的问题,但我实际上无法弄清楚如何在Java中以编程方式进行.

请尝试提供可以执行此操作的确切代码.

Dav*_*ave 8

假设您的输入为N.您知道每组k个连续数字将以N/k为中心.如果N/k以0.5结束,则存在偶数k的解,如果N/k是整数,则存在奇数k.如果存在,解是以N/k为中心的k个整数.

k=1: 15/1 = 15, so 15 (trivial; may want to omit)
k=2: 15/2 = 7.5, so 7,8
k=3: 15/3 = 5, so 4,5,6
k=4: 15/4 = 3.75, so no solution
k=5: 15/5 = 3, so 1,2,3,4,5
k=6: 15/6 = 2.5, so 0,1,2,3,4,5 
etc...
k=15: 15/15 = 1, so -6,-5,-4,-3,-2,-1,0,1,2,3,4,5,6,7,8
Run Code Online (Sandbox Code Playgroud)

您可以轻松修改此限制以限制正面或非负面解决方案.


ing*_*gen 6

我将扩展@MBo 的答案,因为它传达了一个非常干净的算法。Wiki提供了关于算术级数的很好的介绍,为方便起见,复制在下面。

和

推导

在此处输入图片说明

以数字开头a并由n连续数字组成的序列之和:

S = (n/2) * [2 * a + (n-1) * d]

对于连续数字,步长d为 1。

S = (n/2) * [2 * a + (n-1)]

在这里,我们可以过渡到@MBo 的帖子。

P = 2 * S = n * [2 * a + (n-1)]

我们可以迭代所有可能的连续数字计数n并检查结果a是否有效(即a是一个整数)。

让我们考虑一下a

假设 P = n * q => q = 2 * a + (n-1) => 2 * a = q - n + 1 => a = (q - n + 1) / 2

过滤器

1) 我们提到我们可以迭代所有可能的连续数字计数n,但可以 p = n * q肯定地说n需要是 的除数p

  • p % n == 0
  • nMax = (int)Math.sqrt(p)

2)a是整数,a = (q - n + 1) / 2=>(q - n + 1)是偶数 =>q - n是奇数。

  • ((q - n) & 1) == 1

执行

import java.util.*;
import java.lang.Math;
import java.util.stream.IntStream;
import static java.util.stream.Collectors.toList;

public class Progressions
{
    public static void main(String[] args)
    {
        List<List<Integer>> list = Calculate(15);
        System.out.print(list);
    }

    public static List<List<Integer>> Calculate(int s)
    {
        List<List<Integer>> list = new ArrayList<>();
        int p = 2*s;
        int nMax = (int)Math.sqrt(p);
        for (int n=2; n<=nMax; n++) {
            if(p % n == 0) {
                int q = p / n;
                if(((q - n) & 1) == 1) {          
                    int a = (q - n + 1) / 2;
                    list.add(range(a,n));
                }
            }
        }
        return list;
    }

    public static List<Integer> range(int a, int n) {
        return IntStream.range(a, a+n)
            .boxed()
            .collect(toList());
    }
}
Run Code Online (Sandbox Code Playgroud)


MBo*_*MBo 5

连续的数字形成算术级数。如果它从数字开始a并且有n成员,那么它的总和是

S = n * (2 * b + (n-1)) / 2
so
P = 2 * S = n * (2 * b + (n-1))
Run Code Online (Sandbox Code Playgroud)

因此,对于给定的输入 S,我们可以分解2*S为所有可能的整数因数对,P = n * q其中n<=q,然后得到起始数

a = (q - n + 1) / 2
Run Code Online (Sandbox Code Playgroud)

如果 a 是整数(q 和 n的奇数不同),则pair表示从成员(a, n)开始的有效序列an

示例S = 15, 2S = 30

30 = 2 * 15 => n = 2, a = 7  => (7,8)
30 = 3 * 10 => n = 3, a = 4  => (4,5,6)
30 = 5 * 6 =>  n = 5, a = 1  => (1,2,3,4,5)
Run Code Online (Sandbox Code Playgroud)

简单的Python示例:

import math
def getseqs(s):
    print(s)
    p = 2 * s
    for n in range(2, math.ceil(math.sqrt(p))):
        if (p % n == 0):
            q = p // n
            if (((q - n) & 1) == 1):  #compare parity
                a = (q - n + 1) // 2
                seq = list(range(a, a+n))
                print(seq, sum(seq))

getseqs(17)
getseqs(15)
getseqs(72)

17
[8, 9] 17
15
[7, 8] 15
[4, 5, 6] 15
[1, 2, 3, 4, 5] 15
72
[23, 24, 25] 72
[4, 5, 6, 7, 8, 9, 10, 11, 12] 72
Run Code Online (Sandbox Code Playgroud)