Enorme diferença.
Como o nome indica, a doubletem 2x a precisão de [1] . Em geral, a possui 15 dígitos decimais de precisão, enquanto que 7.floatdoublefloat
Veja como o número de dígitos é calculado:
doublepossui 52 bits de mantissa + 1 bit oculto: log (2 53 ) ÷ log (10) = 15,95 dígitos
floatpossui 23 bits mantissa + 1 bit oculto: log (2 24 ) ÷ log (10) = 7,22 dígitos
Essa perda de precisão pode levar ao aumento de erros de truncamento quando cálculos repetidos são feitos, por exemplo,
float a = 1.f / 81;
float b = 0;
for (int i = 0; i < 729; ++ i)
b += a;
printf("%.7g\n", b); // prints 9.000023
enquanto
double a = 1.0 / 81;
double b = 0;
for (int i = 0; i < 729; ++ i)
b += a;
printf("%.15g\n", b); // prints 8.99999999999996
Além disso, o valor máximo de float é de cerca de 3e38, mas o dobro é de aproximadamente 1.7e308, portanto, o uso floatpode atingir "infinito" (ou seja, um número de ponto flutuante especial) muito mais facilmente do que doublepara algo simples, como calcular o fatorial de 60.
Durante o teste, talvez alguns casos de teste contenham esses números enormes, o que pode causar falhas nos programas se você usar flutuadores.
É claro que, às vezes, nem doubleé preciso o suficiente, portanto, temos long double[1] (o exemplo acima fornece 9.000000000000000066 no Mac), mas todos os tipos de ponto flutuante sofrem erros de arredondamento , portanto, se a precisão é muito importante (por exemplo, dinheiro processamento) você deve usar intou uma classe de fração.
Além disso, não use +=para somar muitos números de ponto flutuante, pois os erros se acumulam rapidamente. Se você estiver usando Python, use fsum. Caso contrário, tente implementar o algoritmo de somação Kahan .
[1]: Os padrões C e C ++ não especificam a representação de float, doublee long double. É possível que todos os três sejam implementados como IEEE de precisão dupla. No entanto, para a maioria das arquiteturas (gcc, MSVC; x86, x64, ARM) float é de fato um número de ponto flutuante de precisão única IEEE (binary32) e double é um número de ponto flutuante de precisão dupla IEEE (binary64).