Вопрос № 100843: здраствуйте эксперты.
Программирую на VS2005. При выполнении следующего кода выводится неожиданый результат.
char string[] = "-4.7128";
float flnumber = atof(string);
После выполнения данного кода переменная flNumb...Вопрос № 100968: Необходимо организовать переход между текстовыми файлами. После запуска программы на экран выводится содержимое первого файла, как только программа обнаруживает конец первого файла, происходит очистка поля и выводится содержимое второго файла. Так до...
Вопрос
№ 100.843
здраствуйте эксперты.
Программирую на VS2005. При выполнении следующего кода выводится неожиданый результат.
Как видите, всё нормально. Строки я скопировал с вашего вопроса.
Но.. можете использовать тип double.
PS: среда - VS2005.
--------- Если ничего не помогло - надо читать инструкцию
Ответ отправил: Виктор Пырлик (статус: Студент)
Ответ отправлен: 04.09.2007, 21:25
Отвечает: Maxim V.G.
Здравствуйте, Sulimacom!
Если использовать тип float то на 1000 итераций возникает погрешность. А исспользуя тип double погрешности нет.
double flnumber_ = 0;
double flnumber;
char string[] = "-4.7128";
for (int i = 0; i<1000001; i++){
flnumber = atof(string);
flnumber_ = flnumber * i;
printf("result: %f*%d=%f
",flnumber,i,flnumber_);
}
result: -4.7128*1000000=4712800
А с типом float на третей итерации даёт сбой.
Отсюда вывод: надо использовать тип double!!!
--------- Жить вредно - от неё умирают
Ответ отправил: Maxim V.G. (статус: 4-ый класс)
Ответ отправлен: 05.09.2007, 02:00 Оценка за ответ: 4 Комментарий оценки: переделал свой код для работы с типом double но переменная преобразуется не коректно. Дебагер показывает x -4.7127999999999997 double
Отвечает: Aristos
Здравствуйте, Sulimacom!
Строка преобразуется правильно. Все дело в том, что числа с плавающей точкой имеют ограниченную точность. Так переменная с типом float имеет 7 значащих знаков, с типом double (двойная точность) - 15 знаков. Поэтому не стоит удивляться тому, что 4.71279999f будет равно 4.7128f . Стоит отметит способ задания типа у числовых констант (чтобы различить float и double). В обычной записи (4.7128) тип константы будет double, чтобы указать, что константа имеет тип float необходимо в конце числа приписать символ f. А
константы без десятичной точки будут иметь целочисленные типы. Например:
4.7128 - double
4.7128f - float
4 - int или short или char
4. - double
4.f - float
Следует избегать в коде сравнение на равенство/неравентсво переменых нецелочисленных типов. Отношения больше/меньше работают вполне корректно. И не стоит забывать про типы у констант.
Приложение:
Ответ отправил: Aristos (статус: 5-ый класс)
Ответ отправлен: 05.09.2007, 11:44 Оценка за ответ: 3 Комментарий оценки: Как применить ваш ответ в моём примере
Отвечает: Rockie
Здравствуйте, Sulimacom!
При вычислениях с плавающей точкой в любом случае будет погрешность. Каков результат деления 10/3? На бумаге вы можете записать 3.(3), но в компьютере это число непредставимо, так как количество битов для представления числа конечно.
Могу предложить вам запоминать количество знаков после запятой в строке, а потом округлять полученный результат по этому значению(то есть округлять 4.71279 к 4.7128). Функции округления есть в сети(последние 3 ссылки).
Этот результат вполне ожиданный. Вы можете программировать хоть на паскале хоть на C# - везде одно и тоже. А все дело в стандарте IEEE754 на хранение и обработку чисел типа float. Примерно этот стандарт можно описать так: все числа хранить в удобном для процессора виде. Т.е. числа хранятся в памяти таким образом, чтобы потом с ними процессор мог быстро производить нужные операции. Соответственно число "-4.7128" плохое, а число близкое к нему "-471279999..." - хорошее для работы процессора.
К сожалению этому ни где не учат, когда знакомят с форматом float и поэтому очень часто программист не может понять почему правильно написанная программ начинает глючить.
Так что у меня совет один: пользуйся флоатом только в случае крайней необходимости, иначе можешь на ровном месте зависнуть и на долго. А лучше всего - - забудь, что такой тип есть.
По указанному стандарту только что нашел статью:
"IEEE754-тика угрожает человечеству"
например по адресу http://www.yur.ru/science/computer/IEEE754.htm
Цитата из этой статьи:
"Взрыв ракеты "Пэтриот» в Саудовской Аравии 25 февраля 1991, который привел к гибели 28 человек, связан с ошибками округления."
Ответ отправил: Зелик Колабухин (статус: 3-ий класс)
Ответ отправлен: 06.09.2007, 10:34
Вопрос № 100.968
Необходимо организовать переход между текстовыми файлами. После запуска программы на экран выводится содержимое первого файла, как только программа обнаруживает конец первого файла, происходит очистка поля и выводится содержимое второго файла. Так должно продолжаться до тех пор, пока программа не переберет все имеющиеся текстовые файлы.
Причем все файлы имеют схожие названия такого типа: question_1.txt, question_2.txt, question_3.txt
Как примерно должен выглядеть программный код. Буксую на одном месте. Помогите, пожалуйста!
Отвечает: Sov
Здравствуйте, Stacey_campbell!
Пример для билдера
Приложение:
Ответ отправил: Sov (статус: 6-ой класс)
Ответ отправлен: 05.09.2007, 20:55
Отвечает: Терсков Сергей
Здравствуйте, Stacey_campbell!
Очень похоже га ваш же вопрос № 100831. В моем ответе приведен подобный код с использованием STL. Если имена файлов схожи, то остается только генерировать их в цикле. То есть нужен будет код подобный этому:
См приложение.
Приложение:
Ответ отправил: Терсков Сергей (статус: Студент)
Ответ отправлен: 06.09.2007, 03:29