2015-03-17 3 views
1

Я новичок в языке программирования c. То, что я пытаюсь сделать, - это получить pi в хранилище в произвольной точности и превратить это в строку.произвольное число чисел с плавающей запятой до строки

int calculatePIConst (int preciznost) 
{ 
    //init var 
    mpfr_t x; 
    mpfr_init2 (x, preciznost); 
    //populate pi 
    mpfr_const_pi (x, MPFR_RNDN); 
    //turn to string 
    char abc[preciznost]; 
    int i; 
    //error RUN FINISHED; Segmentation fault; core dumped; real time: 90ms; user: 0ms; system: 0ms 
    // mpfr_get_str (abc, i, 50, 50, x, MPFR_RNDN); 
    //write pi 
    mpfr_printf ("PI = %1.1024RNf\n", x); 
    mpfr_clear (x); 
    return *abc; 
} 

Вот MPFR Lib документация документация http://www.mpfr.org/mpfr-current/mpfr.html#Miscellaneous-Functions

+0

У вас есть комментарий '// переходят к string' затем массиву' символ а [preciznost]; ', который не инициализирован, пока вы возвращаете значение первого элемента в качестве значения функции. –

ответ

1

Из документации вы связаны с:

If ул не является нулевым указателем, то он должен указывать на блок хранения большого достаточно для значения, то есть, по меньшей мере, max (n + 2, 7). Дополнительные два байта для возможного знака минус, а для завершающего нулевого символа, а значение 7 учитывает - @ Inf @ плюс завершающий нулевой символ.

Кроме того, я предполагаю, что вы хотите, чтобы ваш результат в базе 10, не основывают 50.

Попробуйте это:

char abc[preciznost + 2]; /* assuming preciznost >= 5 */ 
    : 
mpfr_get_str (abc, i, 10, 50, x, MPFR_RNDN); 
0

Какое значение вы сходя за preciznost? Я вижу, что вызовы могут обрабатывать очень большие битную точность, и есть опасность, что вы нарушили стек с декларацией

char abc[preciznost]; 

Я предлагаю вам выделить память в куче вместо этого, помня free() позже.

char *abc = malloc(preciznost); 

Хотя неясно, для чего вы будете использовать этот массив. Если это символ массив '0' или '1' битных значений вам понадобится дополнительный байт для nul termintor, так

char *abc = malloc(preciznost+1); 
2

Самый простой способ был бы позволить MPFR выделить строку:

char* abc = NULL; 
abc = mpfr_get_str (NULL, i, 10, 50, x, MPFR_RNDN); 

printf ("PI = %s\n", abc); 

mpfr_clear(x); 
mpfr_free_str(abc); 

Также проверьте эту функцию из C++ wrapper for the MPFR, например:

inline std::string mpreal::toString(const std::string& format) const 
{ 
    char *s = NULL; 
    std::string out; 

    if(!format.empty()) 
    { 
     if(!(mpfr_asprintf(&s, format.c_str(), mpfr_srcptr()) < 0)) 
     { 
      out = std::string(s); 

      mpfr_free_str(s); 
     } 
    } 
    return out; 
} 

дело в том, чтобы использовать mpfr_asprint f, он выделяет и автоматически возвращает строку (то же, что и mpfr_get_str), но также позволяет использовать спецификацию формата.

0

Прототип:

char *mpfr_get_str (char *str, mpfr_exp_t *expptr, int b, size_t n, mpfr_t op, mpfr_rnd_t rnd) 

Есть две неправильные вещи в вашем коде:

  1. массив не является достаточно большим. См. the answer by squeamish ossifrage. Но если вы решите использовать n равным 0, лучше дать MPFR выделить строку (также предложенную Павлом Голобородько во всех случаях).

  2. Второй аргумент должен быть указателем на mpfr_exp_t.Например: mpfr_exp_t e; mpfr_get_str (abc, &e, 10, 50, x, MPFR_RNDN);

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