2012-10-04 2 views
1

Я написал функцию Фибоначчи, используя типы и функции из библиотеки GMP 5.0.2. Но я все время получаю ошибку, когда компилирую ее. Ниже приведены ошибки и код:Функция Fibonacci с использованием GMP 5.0.2 в C

main.c:4:7: error: ‘fib’ declared as function returning an array 
main.c: In function ‘main’: 
main.c:21:10: error: incompatible types when assigning to type ‘mpz_t’ from type ‘int’ 
main.c: At top level: 
main.c:32:7: error: ‘fib’ declared as function returning an array 
main.c: In function ‘fib’: 
main.c:33:28: warning: return makes integer from pointer without a cast [enabled by default] 
main.c:44:3: warning: passing argument 2 of ‘__gmpz_set’ makes pointer from integer without a cast [enabled by default] 
/usr/local/include/gmp.h:1074:21: note: expected ‘mpz_srcptr’ but argument is of type ‘int’ 
main.c:45:3: warning: passing argument 2 of ‘__gmpz_set’ makes pointer from integer without a cast [enabled by default] 
/usr/local/include/gmp.h:1074:21: note: expected ‘mpz_srcptr’ but argument is of type ‘int’ 
main.c:47:3: error: too few arguments to function ‘__gmpz_add’ 
/usr/local/include/gmp.h:696:21: note: declared here 

и код

#include <stdio.h> 
#include <gmp.h> 

mpz_t fib (mpz_t, const mpz_t); 

int main (void) { 
    printf("Before anything\n"); // debugging 

    mpz_t FOUR; mpz_init(FOUR); mpz_add_ui(FOUR, FOUR, 4); 

    printf("Declare FOUR, initilize it, set it to 4\n"); // debugging 

    mpz_t N; mpz_init(N); mpz_add_ui(N, N, 5); 

    printf("Declare N, initilize it, set it to 5\n"); // debugging 

    mpz_t fibFive; mpz_init(fibFive); 

    printf("Declare fibFive, initilize it\n"); // debugging 

    fibFive = fib(N, FOUR); 

    printf("After calling the fib function on fibFive\n"); // debugging 

    gmp_printf("5th fibonacci number is %Zd\n", fibFive); 

    printf("the end\n"); // debugging 

    return 0; 
} 

mpz_t fib (mpz_t n, const mpz_t baseCase) { 
    if (mpz(n, baseCase) < 0) return n; 
    else { 
     mpz_t a, b; 
     mpz_t t1, t2; 

     mpz_init(a); mpz_init(b); 
     mpz_init(t1); mpz_init(t2); 

     mpz_sub_ui(t1, n, 2); 
     mpz_sub_ui(t2, n, 1); 

     mpz_set(a, fib(t1, baseCase)); 
     mpz_set(b, fib(t2, baseCase)); 

     return mpz_add(a, b); 
    } 
} 

И для компиляции я использовал gcc main.c -lgmp

Примечание: Я прочитал руководство по GMP, и я использовал функцию в коде от Integer. Руководство по функциям GMP 5.0.2 Manual - Integer Functions

+1

Короткий ответ, вы не _return_ 'mpz_t' и друзья, вы передать их функции как из-параметров. –

+1

Вы также должны прочитать [это] (http://www.gnu.org/software/gmp/manual/html_node/Parameter-Conventions.html). – ArjunShankar

ответ

2

Соответствующая часть gmp.h (Я не знаю второстепенную версию У меня есть установлен, но это было то же самое в GMP 4, и я не ожидаю, что это скоро изменится) является

typedef struct 
{ 
    int _mp_alloc;   /* Number of *limbs* allocated and pointed 
           to by the _mp_d field. */ 
    int _mp_size;    /* abs(_mp_size) is the number of limbs the 
           last field points to. If _mp_size is 
           negative this is a negative number. */ 
    mp_limb_t *_mp_d;   /* Pointer to the limbs. */ 
} __mpz_struct; 

#endif /* __GNU_MP__ */ 


typedef __mpz_struct MP_INT; /* gmp 1 source compatibility */ 
typedef __mpz_struct mpz_t[1]; 

так что mpz_t массив длины одного содержащего __mpz_struct. Именно по этой причине

main.c:4:7: error: ‘fib’ declared as function returning an array

и тому подобное. Без прототипа, компилятор, очевидно, предполагает неявный INT, таким образом

fibFive = fib(N, FOUR); 

вызывает

main.c:21:10: error: incompatible types when assigning to type ‘mpz_t’ from type ‘int’

Чтобы исправить это, вы должны пройти mpz_t сек, как из-параметры вашей функции (ы) с минимальными изменениями (не то, что ваши показатели выключены, F(0) = 0 условно):

#include <stdio.h> 
#include <gmp.h> 

void fib (mpz_t, mpz_t, const mpz_t); 

int main (void) { 
    printf("Before anything\n"); // debugging 

    mpz_t FOUR; mpz_init(FOUR); mpz_add_ui(FOUR, FOUR, 4); 

    printf("Declare FOUR, initilize it, set it to 4\n"); // debugging 

    mpz_t N; mpz_init(N); mpz_add_ui(N, N, 5); 

    printf("Declare N, initilize it, set it to 5\n"); // debugging 

    mpz_t fibFive; mpz_init(fibFive); 

    printf("Declare fibFive, initilize it\n"); // debugging 

    fib(fibFive, N, FOUR); 

    printf("After calling the fib function on fibFive\n"); // debugging 

    gmp_printf("5th fibonacci number is %Zd\n", fibFive); 

    printf("the end\n"); // debugging 

    return 0; 
} 

void fib (mpz_t res, mpz_t n, const mpz_t baseCase) { 
    if (mpz_cmp(n, baseCase) < 0){ 
     mpz_set(res,n); 
    } else { 
     mpz_t a, b; 
     mpz_t t1, t2; 

     mpz_init(a); mpz_init(b); 
     mpz_init(t1); mpz_init(t2); 

     mpz_sub_ui(t1, n, 2); 
     mpz_sub_ui(t2, n, 1); 

     fib(a, t1, baseCase); 
     fib(b, t2, baseCase); 

     mpz_add(res, a, b); 
    } 
} 
+0

Спасибо Даниэлю очень за объяснение. Было полезно –

Смежные вопросы