将Double转换为Char时的舍入错误

时间:2017-01-27 03:35:48

标签: c char int double

我的任务是在没有外部库的情况下在C中重新创建printf。我正在尝试实现%f功能,精度为6位小数。所以基本上,如果我将15.2554传递给printf函数,则应打印“15.255400”。相反,打印的是“15.255399”。我找到小数位的代码是这样实现的:

print_function(double input){

  int i = 0;
  int temp;
  double temp_dub;
  char temp_char;

  temp = (int)input;

  temp_dub = input - temp;

  while (i < 6){

    temp_dub = temp_dub * 10;
    temp = (int) temp_dub;
    temp_char = (char) (temp+48)

    write(1,&temp_char,1);
    i++;

    temp_dub -= (int) temp_dub;
  }

  return;
}

任何人都可以照亮我,为什么我无法得到尾随的零,而这个数字略低于我输入的15.554?

1 个答案:

答案 0 :(得分:2)

15.2554不能表示为binary64(IEEE-754 double)。如果您使用足够的数字打印输入,则可以看到它:

#include <stdio.h>
#include <stdlib.h>
#include <unistd.h>
// I took the liberty to implement Ari0nhh's changes here
void print_function(double input){
  int i = 0;
  int temp;
  double temp_dub;
  char temp_char;

  temp = (int)input;
  temp_dub = input - temp;

  while (i < 6){
    temp_dub = temp_dub * 10;
    temp = (int) temp_dub;
    temp_char = (char) (temp + 48);
    write(1,&temp_char,1);
    i++;
    temp_dub -= (int) temp_dub;
  }
}

int main(int argc, char **argv){
  double input;
  if(argc != 2){
    fprintf(stderr,"Usage: %s float\n",argv[0]);
    exit(EXIT_FAILURE);
  }
  // checks omitted
  input = strtod(argv[1],NULL);
  printf("INP %.20g\n",input);
  print_function(input);
  putchar('\n');
  exit(EXIT_SUCCESS);
}

您会看到15.2554打印为15.255399999999999849。所以你需要在这里手动滚动,抱歉。