可能的4位数字,其各个数字的总和等于n

时间:2019-01-22 19:40:30

标签: c

我正在使用C语言中的循环制作这个小程序,我必须找到可能的4位数字的总数,其个位数之和将等于n (用户输入)。

但是由于某种原因,它不起作用。 编辑:很抱歉为您提供了不正确的解释,当我执行该程序时,它给了我在arr1,arr2,arr3中的长随机数

#include<stdio.h>

int main()
{
    int num,i,j,k,l,n,n1,n2,n3,pos=0;
    int arr0[100],arr1[100],arr2[100],arr3[100];
    printf("enter the number(must be an Integer!) of which you want to find out possibilities of 4 division\n");
    scanf("%d",&num);

    n=num-3;
    n1=n-2;
    n2=n1-1;

    for(i=1;i<=n;i++)
    {
        n1=num-i;
        for(j=1;i<=n1;j++)
        {
            n2=n1-j;
            for(k=1;i<=n2;k++)
            {
                n3=n2-k;
                for(l=1;i<=n3;l++)
                {
                    arr0[pos]=i;
                    arr1[pos]=j;
                    arr2[pos]=k;
                    arr3[pos]=l;
                    pos++;
                }
            }
        }
    }

    for(i=1;i<pos;i++)
    {
        printf("%d%d%d%d\n",arr0[pos],arr1[pos],arr2[pos],arr3[pos]);
    }

    return(0);
}

2 个答案:

答案 0 :(得分:0)

一些错误...

您正在通过pos为某些数组建立索引,这并没有太大帮助。

我已经运行了您的代码,它似乎循环了很长时间。正如其他人提到的那样,您并没有将数字输入限制为0-9。另外,您的某些数组会获得百搭/较大的值。

您可以使用嵌套循环来执行此操作。也就是说,迭代数字组合,但是我认为您只需要一个4元素数组。也就是说,生成数字字符串并对其进行测试,如果数字字符串有效(即,数字的总和与num相匹配),则将其加到总和中。


可以使用4个嵌套循环来执行此操作, 但是如果位数是任意的(可以在运行时指定)怎么办?

使用n位的可变长度数组,并通过执行来增加它们是嵌套数组的一种替代方法

我无法理解您的算法,因此我从头开始创建了一个版本。它比我认为您的逻辑试图实现的要简单。

它不会询问用户一个num值,而是测试所有可能的num值。

也许这会给您一些想法,可以帮助您了解自己的版本所发生的情况。特别要注意的是,当数字达到10时如何处理结转/翻转。

无论如何,这就是我的想法。它测试num范围内的所有0-9999值,总共花费0.8秒。

一旦给定的num失败(即没有匹配的数字组合),我们将尽早停止,因为没有数字组合会再次匹配。使用早期转义选项-f,程序耗时8ms。

#include <stdio.h>
#include <stdlib.h>

int opt_f;                              // 1=test all numbers
int opt_r;                              // 1=print lowest to highest
int opt_z;                              // 1=exclude anything with leading 0
int opt_v;                              // 1=output matching numbers
int opt_N;                              // num value to use
int opt_W;                              // digit width

int
test(int num,const int *digits)
{
    int sum = 0;
    int digidx;
    int match;

    for (digidx = 0;  digidx < opt_W;  ++digidx)
        sum += digits[digidx];

    match = (sum == num);

    // decide which digit is most significant
    if (opt_r)
        digidx = opt_W - 1;
    else
        digidx = 0;

    // ensure number has no leading zeroes
    if (opt_z) {
        if (! digits[digidx])
            match = 0;
    }

    return match;
}

int
calc(int num)
{
    int digits[opt_W];
    int showflg = 1;
    int carry;
    int tot = 0;

    // reset digit string to all zeroes
    for (int digidx = 0;  digidx < opt_W;  ++digidx)
        digits[digidx] = 0;

    while (1) {
        // test number and print if it matches
        if (test(num,digits)) {
            if (tot == 0) {
                printf("\n");
                printf("NUM: %d\n",num);
            }

            tot += 1;

            // output the number
            if (opt_v) {
                printf("  ");
                if (! opt_r) {
                    for (int digidx = 0;  digidx < opt_W;  ++digidx)
                        printf("%d",digits[digidx]);
                }
                else {
                    for (int digidx = opt_W - 1;  digidx >= 0;  --digidx)
                        printf("%d",digits[digidx]);
                }
                printf("\n");
            }
        }

        // increment to next digit string
        carry = 0;
        for (int digidx = 0;  digidx < opt_W;  ++digidx) {
            // increment the current digit
            digits[digidx] += 1;

            // see if we get a carry out on this digit -- bug out if not
            carry = (digits[digidx] > 9);
            if (! carry)
                break;

            // reset this digit to zero
            digits[digidx] = 0;
        }

        // carry out from most significant digit means stop
        if (carry)
            break;
    }

    if (tot)
        printf("TOT: %d\n",tot);

    return tot;
}

int
main(int argc,char **argv)
{
    char *cp;

    opt_f = 1;
    opt_r = 1;
    opt_z = 1;
    opt_v = 0;
    opt_W = 4;

    --argc;
    ++argv;

    for (;  argc > 0;  --argc, ++argv) {
        cp = *argv;
        if (*cp != '-')
            break;

        switch (cp[1]) {
        case 'f':  // flip test all numbers
            opt_f = ! opt_f;
            break;

        case 'r':  // flip low-to-high
            opt_r = ! opt_r;
            break;

        case 'v':  // flip verbosity
            opt_v = ! opt_v;
            break;

        case 'z':  // flip skip on leading zeroes
            opt_z = ! opt_z;
            break;

        case 'N':  // num value to use
            opt_N = atoi(cp + 2);
            break;

        case 'W':  // set digit width
            opt_W = atoi(cp + 2);
            break;
        }
    }

    // get upper limit of number to test
    int lim = 1;
    for (int num = 1;  num <= opt_W;  ++num)
        lim *= 10;

    printf("WID: %d (%d)\n",opt_W,lim);

    // test all numbers within the range
    int num;
    if (opt_z && (! opt_f))
        num = 1;
    else
        num = 0;
    if (opt_N) {
        num = opt_N;
        lim = num + 1;
    }
    for (;  num < lim;  ++num) {
        if (calc(num))
            continue;
        if (! opt_f)
            break;
    }

    return 0;
}

这是程序输出:

WID: 4 (10000)

NUM: 1
TOT: 1

NUM: 2
TOT: 4

NUM: 3
TOT: 10

NUM: 4
TOT: 20

NUM: 5
TOT: 35

NUM: 6
TOT: 56

NUM: 7
TOT: 84

NUM: 8
TOT: 120

NUM: 9
TOT: 165

NUM: 10
TOT: 219

NUM: 11
TOT: 279

NUM: 12
TOT: 342

NUM: 13
TOT: 405

NUM: 14
TOT: 465

NUM: 15
TOT: 519

NUM: 16
TOT: 564

NUM: 17
TOT: 597

NUM: 18
TOT: 615

NUM: 19
TOT: 615

NUM: 20
TOT: 597

NUM: 21
TOT: 564

NUM: 22
TOT: 519

NUM: 23
TOT: 465

NUM: 24
TOT: 405

NUM: 25
TOT: 342

NUM: 26
TOT: 279

NUM: 27
TOT: 219

NUM: 28
TOT: 165

NUM: 29
TOT: 120

NUM: 30
TOT: 84

NUM: 31
TOT: 56

NUM: 32
TOT: 35

NUM: 33
TOT: 20

NUM: 34
TOT: 10

NUM: 35
TOT: 4

NUM: 36
TOT: 1

答案 1 :(得分:-1)

好吧,我想找出可能的4位数字,这些数字的总和等于某个分配的数字 例如:5 = 1112 这是我更新的代码,但是现在我要确保没有重复:/

#include<stdio.h>

int main()
{
int num,m,i,j,k,l,n,n1,n2,n3,pos=0;
int a0[100],a1[100],a2[100],a3[100];
printf("enter the number(must be an Integer!) of which you want to find out possibilities of 4 division\n");
scanf("%d",&num);

while(num<4)
{
    printf("**ERROR** please enter a valid number(Integer) that can be divided into 4 division\n");
    scanf("%d",&num);
}

for(i=1;i<=9;i++)
{
    for(j=1;j<=9;j++)
    {
        for(k=1;k<=9;k++)
        {
            for(l=1;l<=9;l++)
            {
                if((i+j+k+l)==num)
                {
                a0[pos]=i;
                a1[pos]=j;
                a2[pos]=k;
                a3[pos]=l;
                pos+=1;
                }
            }
        }
    }
}

for(m=0;m<pos;m++)
{
    printf("%d%d%d%d\n",a0[m],a1[m],a2[m],a3[m]);
}

return(0);
}