将double/float转换为字符串

pho*_*xis 27 c string floating-point

我需要将浮点数转换为十进制(或其他基数)中的等效字符串.转换在首先需要在格式来进行xE+0,其中x是浮点数.

这个想法我已经是浮点数首先截断到一个临时整数,则该整数转换成字符串,然后再考虑小数部分,用它乘以10而小数部分不成了0.将小数部分转移到小数点的左侧后,再次将整数应用于字符串函数,并将小数部分转换为字符串.有没有更好的方法,哪个比这更快?这种方法会引起任何副作用吗?

要将浮点数转换为指数表示,我应该如上所述,然后调整功率吗?或者直接对IEEE 754浮点表示进行位掩码,并将每个部分转换为字符串.

注意:没有其他功能可以使用,因为我可以访问绝对没有库函数.这段代码进入玩具内核.

小智 26

使用snprintf()stdlib.h.为我工作.

double num = 123412341234.123456789; 
char output[50];

snprintf(output, 50, "%f", num);

printf("%s", output);
Run Code Online (Sandbox Code Playgroud)

  • 我不能使用任何标准的库函数,因为我没有工作的平台是可用的. (8认同)
  • 我用 GCC 和 LLVM/Clang 编译了这段代码——结果是“123412341234.123459”,而不是“123412341234.123456789”。这个答案部分正确,因为它只适用于小范围的浮点值。 (2认同)

R..*_*R.. 19

唯一确切的解决方案是对基本转换执行任意精度的十进制算术,因为精确值可能非常长 - 对于80位long double,最多约10000个小数位.幸运的是,对于IEEE来说,它"仅"大约700个左右double.

相反,使用单个十进制数字,而不是工作基数为10亿(10位的最高功率适合32位整数),然后将这些"基数为10亿的数字"转换为9位十进制数字在计算结束时.

LGPL MIT许可下,我有一个非常密集(相当难读)但有效的实现:

http://git.musl-libc.org/cgit/musl/blob/src/stdio/vfprintf.c?h=v1.1.6

如果你去除所有的hex浮动支持,infinity/nan支持,%g/ %f/ %e变体支持,舍入(如果你只需要确切的答案就永远不需要),以及你可能不需要的其他东西,剩下的代码相当简单.


wor*_*rty 6

去看一下C库中的printf()实现"%f".


小智 5

我知道这可能是不必要的,但我做了一个将浮点数转换为字符串的函数:

代码:

#include <stdio.h>

/** Number on countu **/

int n_tu(int number, int count)
{
    int result = 1;
    while(count-- > 0)
        result *= number;

    return result;
}

/*** Convert float to string ***/
void float_to_string(float f, char r[])
{
    long long int length, length2, i, number, position, sign;
    float number2;

    sign = -1;   // -1 == positive number
    if (f < 0)
    {
        sign = '-';
        f *= -1;
    }

    number2 = f;
    number = f;
    length = 0;  // Size of decimal part
    length2 = 0; // Size of tenth

    /* Calculate length2 tenth part */
    while( (number2 - (float)number) != 0.0 && !((number2 - (float)number) < 0.0) )
    {
         number2 = f * (n_tu(10.0, length2 + 1));
         number = number2;

         length2++;
    }

    /* Calculate length decimal part */
    for (length = (f > 1) ? 0 : 1; f > 1; length++)
        f /= 10;

    position = length;
    length = length + 1 + length2;
    number = number2;
    if (sign == '-')
    {
        length++;
        position++;
    }

    for (i = length; i >= 0 ; i--)
    {
        if (i == (length))
            r[i] = '\0';
        else if(i == (position))
            r[i] = '.';
        else if(sign == '-' && i == 0)
            r[i] = '-';
        else
        {
            r[i] = (number % 10) + '0';
            number /=10;
        }
    }
}
Run Code Online (Sandbox Code Playgroud)

  • 这最多可以正确打印一些小的浮点数。R.. 在 2011 年已经发布了所有双精度数字的正确答案,现在添加一个不正确的数字有什么价值? (2认同)