如何存储多达1,000,000,000个元素

时间:2017-07-13 10:12:05

标签: c arrays size

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

int max_b(int,int);
int max(int[],int);

int main(){

    int num_tests;
    scanf("%d",&num_tests);
    int array_n[num_tests];
    int array_b[num_tests];
    int i,j;
    for (i=0;i<num_tests;i++){
        scanf("%d %d",&array_n[i],&array_b[i]);
    }
    for (j=0;j<num_tests;j++){
        int A = 1;
        int N = array_n[j];
        int B = array_b[j];
        int max_num_b;
        max_num_b = max_b(N,B);
        int array2[max_num_b];
        int k;
        for (k=0;k<max_num_b;k++){
            int num_a,num_b;
            num_a = N-(k+1)*B;
            num_b = k+1;
            array2[k] = num_a*num_b;            
        }
        printf("%d\n",max(array2,max_num_b));
    }

}

int max(int array[],int a){
    int max_num = 0,i;
    for (i=0;i<a;i++){
        if (array[i] > max_num){
            max_num = array[i];
        }
    }
    return max_num;
}

int max_b(int n,int b){
    return n/b;
}

我的第一个输入是测试用例数量T(比如1),第二个输入是1,000,000,000 1。因此,代码尝试形成10 ^ 9大小的数组,程序最终显示分段错误。然而,代码运行良好高达1,000,000 1.如何存储多达10 ^ 9个元素。如果它不可能那么我怎么能存储这么多数字。 我应该使用malloc,如果是,那么如何。任何帮助将不胜感激。

4 个答案:

答案 0 :(得分:3)

根本不需要存储这些数据。只需动态处理即可。

据我所知,以下代码产生与您发布的代码相同的结果,但不使用任何数组。

#include <stdio.h>

int main() {
    int k, t, N, B, max, num_tests;
    scanf("%d", &num_tests);
    while (num_tests--) {
        scanf("%d %d", &N, &B);
        for (k=N/B,max=0; k>0; k--) {
            t = (N-k*B) * k;
            if (t > max) max = t;
        }
        printf("%d\n", max);
    }
    return 0;
}

答案 1 :(得分:1)

对于两个阵列中的十亿int,假设您有32位int,则需要近8GiB的存储空间。

这是一个非常大的内存,使用标准C函数最好的选择是通过malloc()请求它们 - 如果你的地址空间足够大(在i386上,它也会是小,但在amd64它应该没问题如果系统可以提供那么多内存,以下应该有效:

int main(){

    unsigned long num_tests;
    scanf("%lu",&num_tests);

    int *array_n = malloc((size_t)num_tests * sizeof(*array));
    if (!array_n)
    {
        fputs("couldn't allocate array_n\n", stderr);
        return 1;
    }
    int *array_b = malloc((size_t)num_tests * sizeof(*array));
    if (!array_b)
    {
        fputs("couldn't allocate array_b\n", stderr);
        free(array_n);
        return 1;
    }

    size_t i,j;
    for (i=0;i<num_tests;i++){
        scanf("%d %d",&array_n[i],&array_b[i]);
    }

    // rest of code

    free(array_b);
    free(array_n);
}

注意我更改了scanf()以阅读unsigned long,只是为了确定。但它仍然没有防弹。

答案 2 :(得分:0)

在运行时确定大小时, NOT 应使用变长数组声明。

我建议您改用malloc()。替换以下行

int num_tests;
scanf("%d",&num_tests);
int array_n[num_tests];
int array_b[num_tests];

使用

int num_tests, *array_n, *array_b;

scanf("%d", &num_tests);

array_n = malloc(num_tests * sizeof(int));
if (array_n == NULL)
{
    printf("Memory allocation error for array_n!\n");
    return -1;
}

array_b = malloc(num_tests * sizeof(int));
if (array_b == NULL)
{
    /* cleanup */
    free(array_n);

    printf("Memory allocation error for array_b!\n");
    return -1;
}

正如其他评论所指出的,1,000,000,000个元素需要大约4GB的内存(两倍于你有两个数组)。因此,您可能会耗尽内存分配这么多整数。

答案 3 :(得分:-1)

首先,初始化数组时,大小必须是常量。所以请改用#define NUM_TESTS 1000000000。 其次,由于整数大小为4字节,因此10 ^ 9整数需要4 000 000 000 B,等于4 GB。它在堆栈上非常“硬”到4 GB。您应该使用文件,或者,如果您的所有值都小于256,则可以使用char代替。它仍然是1 GB,但这样“更容易”获得。