如何为大整数实现整数数组加法器?

时间:2015-08-23 13:17:21

标签: c arrays integer add biginteger

由于C不支持Big Integers作为JAVA,我试图实现一个整数加法器函数,该函数将两个整数数组作为参数并返回指向它们的和的指针,该指针又是一个数组。这是我的代码。

#include<stdio.h>
#include<stdlib.h>
int max(int a,int b) {
    return a < b ? b : a;
}

int* decimalAdder (int* p, int* q) {
    int size1, size2, i;
    size1 = sizeof(p) / sizeof(int);
    size2 = sizeof(q) / sizeof(int);
    int m = max(size1, size2) + 1;
    int* c = (int*)malloc(m * sizeof(int));
    int carry = 0;
    for(i=0 ; i<m ; i++) {
        c[i] = 0;
        if(i < size1 && i < size2) {
            c[i] += p[i] + q[i] + carry;
            if(c[i] >= 10) {
                c[i] = c[i] % 10;
                carry = 1;
            }
            else
                carry = 0;
        }
        else if(i < size1) {
            c[i] += p[i] + carry;
            if(c[i] >= 10) {
                c[i] = c[i] % 10;
                carry = 1;
            }
            else
                carry = 0;
        }
        else if(i < size2) {
            c[i] += q[i] + carry;
            if(c[i] >= 10) {
                c[i] = c[i] % 10;
                carry = 1;
            }
            else
                carry = 0;
        }
        else
            c[i] += carry;
    }
    return c;
}

//Test program
int main() {
    int a[] = {7, 5, 3, 6};
    int b[] = {3, 5, 3};
    int* sum;
    int i;
    sum = decimalAdder(a, b);
    int size = sizeof(sum) / sizeof(int);
    for(i = size ; i >= 0 ; i--)
        printf("%d", sum[i]);
    free(sum);
    sum=NULL;
    return 0;
}

输出10 我哪里错了?我错过了什么?

3 个答案:

答案 0 :(得分:2)

如评论中所述,sizeof(p)sizeof(q)sizeof(int *)相同。您需要将真正的数组大小作为参数传递给decimalAdder()

首先,更改decimalAdder()以接收尺寸:

int *decimalAdder (int *p, size_t size1, int *q, size_t size2) {
    int i;
    int m = max(size1, size2) + 1;
    int *c = malloc(m * sizeof(int));
    /* ... */
}

您询问如何确定数组的大小以将其传递给decimalAdder()。好吧,如果您动态分配了数组,那么您可能知道它的大小(它与之前传递给malloc(3)的大小相同)。

如果数组是堆栈分配的(这里就是这种情况),你可以使用sizeof()中使用的main()方法,但只能在声明数组的函数内部(因为尽快)当你将一个本地数组传递给另一个函数时,它会衰减成指向第一个元素的指针,你不能再确定它的大小了。

因此,在这种情况下,您可以将main()更改为:

int main(void) {
    int a[] = {7, 5, 3, 6};
    int b[] = {3, 5, 3};
    size_t size1 = sizeof(a)/sizeof(a[0]);
    size_t size2 = sizeof(b)/sizeof(b[0]);
    int* sum;
    int i;
    sum = decimalAdder(a, size1, b, size2);    
    int size = max(size1, size2);

    for(i = size ; i >= 0 ; i--)
        printf("%d", sum[i]);

    free(sum);
    sum=NULL;

    return 0;
}

请注意,int size = sizeof(sum) / sizeof(int);无法按预期方式运行:sum不是真正的数组,它是指向int的指针,因此sizeof(sum)sizeof(int *)您分配的数组的大小。 C不跟踪它,你必须自己做(而不是Java)。

答案 1 :(得分:1)

  

但如果不知道如何确定p和q的真实大小?

像这样:

#include<stdio.h>

void returnLen(int length){
    printf("The length of Array is:\t%d\n",length);
}

int main(void){
    int array[] = {7, 5, 3, 6, 1, 9, 3, 6, 2, 10, 55};
    int length = sizeof array / sizeof array[0];

    returnLen(length);
    return 0;
}

输出:

  

Array的长度为:11

答案 2 :(得分:0)

因为C中的整数数组是一个简单类型,所以在一般情况下它不会携带有关其大小的信息。有很多方法可以解决这个问题。 Michi的答案对于静态分配的数组是正确的,如果你总是知道你将使用多少个数组元素,这可能足以满足你的需求。但是,如果是这样的话,那么整个练习都没有实际意义,因为你可以使用宏观常量并获得相同的结果。

最终,您最终要做的是创建一个可用于携带数字位数(或多位数元素)的数据结构。根据这段代码的使用方式,这样的事情可能有用:

struct myArray{
    int length;
    int *digits;
};

这意味着您必须管理结构的内存(分配,释放,调整大小等)。此外,您可以考虑使用#include和int64_t或uint64_t作为数组元素,因为您可以使用更少的单元格来表示给定的大型int。

数据结构(上图)绝不是唯一的解决方案。您也可以使用链接列表(尽管如果您要做的只是对节点进行简单算术,那么它的重量相当大。)