使用malloc()函数设置全局数组大小获取转储核心

时间:2018-12-24 17:49:27

标签: c

我有一个名为Environment.NewLine的全局数组变量。然后在我的int *PRIME_ARRAY函数中,询问用户该数组的长度,将其保存在main中,并用int quantita进行设置。

当我没有编译错误,但是当我执行它并插入一个数字(例如“ 7”)时,它会产生核心转储错误。我尝试以“新手方式”对其进行调试,在所有代码中放入PRIME_ARRAY = malloc(sizeof(int) * quantita)短语。这样看来问题出在使用printf()函数。

(我必须将数组作为全局变量。malloc()必须仅将next_prime()作为参数)

int last

3 个答案:

答案 0 :(得分:0)

PRIME_ARRAY存储为本地变量,而不是全局变量。然后更改next_prime的参数列表以包括数组的基地址及其大小。您使用sizeof来给出基本指针的大小,即您计算机上的字大小。相反,您需要将quantita变量传递给next_prime函数。

答案 1 :(得分:0)

正如Perette Barella和Yuri J在评论中所说,错误是sizeof(PRIME_ARRAY)在这种情况下返回了指针的大小。 sizeof(array)仅在将数组声明为数组(因此具有静态长度)时才能正常工作。 (例如int array[7]int array[] = {1, 2, 3}

要修复代码,我只需添加一个全局变量调用int array_lenght,将scanf("%i", &quantita);替换为scanf("%i", &array_length);,将i < sizeof(PRIME_ARRAY)/sizeof(int)替换为i < array_lenght

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

int next_prime(int last);

int *PRIME_ARRAY, array_lenght;

int main(void){

  printf("Quanti numeri primi vuoi stampare ? ");

  scanf("%i", &array_lenght);

  PRIME_ARRAY = malloc(sizeof(int) * array_lenght);

  int last = 2;

  for (int i = 0; i < array_lenght; i++){

    PRIME_ARRAY[i] = last;

    last = next_prime(last);

  }

  free(PRIME_ARRAY);

  printf("\n");

  return 0;

}

int next_prime(int last){

  printf("%i ", last);

  bool isPrime = false;

  do {

    last++;

    for (int i = 0; i < array_lenght; i++){

      if (last % PRIME_ARRAY[i] != 0) isPrime = true; break;

    }

  } while (!isPrime);

  return last;

}

答案 2 :(得分:0)

Besides the memory management problems, there are ohter issues in OP's code (even in the one posted as answer):

int next_prime(int last)
{
    printf("%i ", last);
    bool isPrime = false;
    do {
        last++;
        for (int i = 0; i < array_lenght; i++) {
            if (last % PRIME_ARRAY[i] != 0) isPrime = true; break;
            //                            ^^^^^^^^^^^^^^^^^^^^^^^^          
        }
    } while (!isPrime);
    return last;
}

Due to do the lack of brackets, needed to define the scope of the if clause, the nested for-loop isn't actually a loop and the whole function acts as if it was written as:

int next_prime(int last)
{
    printf("%d ", last);
    do {
        last++;  
    } while (last % PRIME_ARRAY[0] == 0);
    return last;
}

As a matter of fact, they both generate the wrong output: all the odds, not only the primes. E.g. the first 20 numbers found are:

2 3 5 7 9 11 13 15 17 19 21 23 25 27 29 31 33 35 37 39

Another issue is that the range of that loop should be limited to the already known primes, not to the entire array, which is uninitialized.

An easy fix, without adding any other global variable (there are too many of those already) could be the following snippet.

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

int next_prime(int last);

int *PRIME_ARRAY, array_length;

int main(void)
{
    printf("How many prime numbers do you want to print? ");

    if (scanf("%d", &array_length) != 1  ||  array_length < 1)
        return EXIT_FAILURE;

    // Allocate and initialize to zero the array of primes
    PRIME_ARRAY = calloc(array_length + 1, sizeof *PRIME_ARRAY);
    if (!PRIME_ARRAY)
        return EXIT_FAILURE;

    int last = 0;
    for (int i = 0; i < array_length; i++)
    {
        // First find the next prime, then print it. Move all the
        // update logic to the called function
        last = next_prime(last);
        printf("%d ", last);
    }
    putchar('\n');

    free(PRIME_ARRAY);

    return EXIT_SUCCESS;
}

int next_prime(int last)
{
    bool has_factors;
    int i;
    do {
        ++last;
        has_factors = false;
        // Check only the known primes
        for (i = 0; PRIME_ARRAY[i] != 0; i++)
        {
            if (last % PRIME_ARRAY[i] == 0)
            {
                has_factors = true;
                break;
            }
        }
    } while ( has_factors  ||  last <= 1 );
    // Update here the array of primes, if there's space left
    if ( i < array_length )
        PRIME_ARRAY[i] = last;

    return last;
}