Мне нужно выполнить простое умножение 400 * 256.3. Результат 102520. Прямо вперед и просто. Но реализовать это умножение в C++ (или C) немного сложно и сбивает с толку.Рекомендации по умножению поплавка в C++ или C?
Я понимаю, что число с плавающей запятой не представлено, как в компьютере. Я написал код, чтобы проиллюстрировать ситуацию. Выход также прилагается.
Итак, если я делаю умножение с использованием переменной типа float, я подвергаюсь ошибке округления. Использование переменной двойного типа позволило бы избежать проблемы. Но предположим, что у меня очень ограниченный ресурс встроенной системы, и я должен оптимизировать тип переменной, насколько это было возможно, как я могу выполнить умножение с помощью переменной типа float и не подвержен ошибкам округления?
Я знал, что математика с плавающей запятой, выполненная компьютером, вообще не сломана. Но мне любопытно, как лучше всего выполнять математику с плавающей запятой. 256.3 - это просто значение для иллюстрации. Я не знаю, какое значение с плавающей запятой я получу во время выполнения. Но это точно, значение с плавающей запятой.
int main()
{
//perform 400 * 256.3
//result should be 102520
float floatResult = 0.00f;
int intResult = 0;
double doubleResult = 0.00;
//float = int * float
floatResult = 400 * 256.3f;
printf("400 * 256.3f = (float)->%f\n", floatResult);
//float = float * float
floatResult = 400.00f * 256.3f;
printf("400.00f * 256.3f = (float)->%f\n", floatResult);
printf("\n");
//int = int * float
intResult = 400 * 256.3f;
printf("400 * 256.3f = (int)->%d\n", intResult);
//int = float * float;
intResult = 400.00f * 256.3f;
printf("400.00f * 256.3f = (int)->%d\n", intResult);
printf("\n");
//double = double * double
doubleResult = 400.00 * 256.3;
printf("400.00 * 256.3 = (double)->%f\n", doubleResult);
//int = double * double;
intResult = 400.00 * 256.3;
printf("400.00 * 256.3 = (int)->%d\n", intResult);
printf("\n");
//double = int * double
doubleResult = 400 * 256.3;
printf("400 * 256.3 = (double)->%f\n", doubleResult);
//int = int * double
intResult = 400 * 256.3;
printf("400 * 256.3 = (int)->%d\n", intResult);
printf("\n");
//will double give me rounding error?
if (((400.00 * 256.3) - 102520) != 0) {
printf("Double give me rounding error!\n");
}
//will float give me rounding error?
if (((400.00f * 256.3f) - 102520) != 0) {
printf("Float give me rounding error!\n");
}
return 0;
}
Ответ прост: вы не можете. Проблема округления «встроена» на компьютерах с использованием формата с плавающей запятой IEEE, что почти все. –
Возможный дубликат [Является ли математика с плавающей запятой?] (Http://stackoverflow.com/questions/588004/is-floating-point-math-broken) – Olaf
Значение 256.3f также лежит на вас, и вы не можете избежать этого , – 2501