fp числа
От: Аноним  
Дата: 18.07.06 09:21
Оценка:
Есть примерно такой код:
double y_min = -7.0;
double y_step = 1.4;
for(int i = 0; i <= 10; ++i)
{
    std::ostringstream oss;
    oss << (y_min + i*y_step);
    ...
}

Проблема в том, что при i == 5, в oss в релизе выводится число 8.88178e-16, хотя в дебаге все нормально — выводится 0. (VS 7.1)
В чем дело?
Re: fp числа
От: LuciferMoscow Россия  
Дата: 18.07.06 09:23
Оценка:
Здравствуйте, Аноним, Вы писали:

А>Есть примерно такой код:

А>
А>double y_min = -7.0;
А>double y_step = 1.4;
А>for(int i = 0; i <= 10; ++i)
А>{
А>    std::ostringstream oss;
А>    oss << (y_min + i*y_step);
А>    ...
А>}
А>

А>Проблема в том, что при i == 5, в oss в релизе выводится число 8.88178e-16, хотя в дебаге все нормально — выводится 0. (VS 7.1)
А>В чем дело?
Поищи вопросы на тему сравнения double с нулем. Обсуждалось много раз
Re[2]: fp числа
От: Аноним  
Дата: 18.07.06 09:55
Оценка:
Здравствуйте, LuciferMoscow, Вы писали:

LM>Поищи вопросы на тему сравнения double с нулем. Обсуждалось много раз


А как это мне поможет? Мне нужно, чтобы не выводились цифры в 16-м знаке после запятой.
Вместо нуля может быть любое другое число. oss.precision(5) почему-то не помогает.
И почему в дебаге работает?
Re[3]: fp числа
От: LuciferMoscow Россия  
Дата: 18.07.06 10:15
Оценка:
Здравствуйте, Аноним, Вы писали:

А>Здравствуйте, LuciferMoscow, Вы писали:


LM>>Поищи вопросы на тему сравнения double с нулем. Обсуждалось много раз

А>А как это мне поможет? Мне нужно, чтобы не выводились цифры в 16-м знаке после запятой.
А>Вместо нуля может быть любое другое число. oss.precision(5) почему-то не помогает.
А ты найди темы и почитай.

А>И почему в дебаге работает?

Потому, что в дебагере он округлил по всей видимости
Re: fp числа
От: KosTiger Россия  
Дата: 18.07.06 11:09
Оценка:
Здравствуйте, Аноним, Вы писали:

А>Есть примерно такой код:

А>
А>double y_min = -7.0;
А>double y_step = 1.4;
А>for(int i = 0; i <= 10; ++i)
А>{
А>    std::ostringstream oss;
А>    oss << (y_min + i*y_step);
А>    ...
А>}
А>

А>Проблема в том, что при i == 5, в oss в релизе выводится число 8.88178e-16, хотя в дебаге все нормально — выводится 0. (VS 7.1)
А>В чем дело?

Это вопрос для общего развития или для решения проблемы?

Если для решения, то смотри форматирование в stream-ах.

   std::ostringstream oss;
   oss.setf(ios_base::fixed, ios_base::floatfield);
   oss.precision(2);


А причиной может быть оптимизация — попробуй
double volatile y_min = -7.0;
double volatile y_step = 1.4;
...
Re[2]: fp числа
От: Аноним  
Дата: 18.07.06 12:05
Оценка:
Здравствуйте, KosTiger, Вы писали:

KT>Это вопрос для общего развития или для решения проблемы?

Для решения проблемы.
KT>Если для решения, то смотри форматирование в stream-ах.

KT>
KT>   std::ostringstream oss;
KT>   oss.setf(ios_base::fixed, ios_base::floatfield);
KT>   oss.precision(2);
KT>

Ага, спасибо, но к сожалению это не подойдет, т.к.:
— очень желательно, чтобы в случае целых числе выводилось 0 1 2 3... (как и происходит в дебаге), а не 0.00, 1.00, 2.00, 3.00...
— y_min может быть числом порядка 0.001 (и y_step соответственно), в этом случае придется ставить precision ~ 5,
а это значит, что целые числа станут выглядеть еще менее привлекательно 1.00000 и т.д.


KT>А причиной может быть оптимизация — попробуй

KT>
KT>double volatile y_min = -7.0;
KT>double volatile y_step = 1.4;
KT>...
KT>

Не помогло.

Непонятно почему число 8.88178*10^-16 не округляется до нуля само по себе, хотя с другими числами вроде все в порядке, поэтому я пока ограничился проверкой на ноль: IF |y_min + i*y_step — 0.0| < 0.000001 THEN oss << 0.0.

Кстати, а при помощи sprintf можно добиться чисел типа 1, 2, 3... чтобы не было точек если они не нужны и при этом задавать точность?
Re[3]: fp числа
От: Roman Odaisky Украина  
Дата: 18.07.06 15:45
Оценка:
Здравствуйте, Аноним, Вы писали:

А>Кстати, а при помощи sprintf можно добиться чисел типа 1, 2, 3... чтобы не было точек если они не нужны и при этом задавать точность?


А как он определит? 3.001 — нужна точка? 3.000001 — нужна? 3.000000000000000000000000000000000000000000000000001? У тебя там есть число 1.4, это 1 2/5. На досуге запиши 1 2/5 двоичной дробью. (У меня вышло 1,011001100110011001100итакдалее — кто хочет проверить?) Дробь бесконечная, потому и возникают погрешности в Nдцатом разряде.

Кстати, для потоков можно устанавливать форматирование чуть покрасивее:

stream << std::fixed << std::setprecision(N) << value; // #.000
До последнего не верил в пирамиду Лебедева.
Re[4]: fp числа
От: ant_katcin Россия  
Дата: 19.07.06 13:56
Оценка:
Здравствуйте, Roman Odaisky, Вы писали:

RO>Здравствуйте, Аноним, Вы писали:


А>>Кстати, а при помощи sprintf можно добиться чисел типа 1, 2, 3... чтобы не было точек если они не нужны и при этом задавать точность?


да можно. для этого есть формат "%g"
... << RSDN@Home 1.1.4 stable SR1 rev. 568>>
Re: fp числа
От: ant_katcin Россия  
Дата: 19.07.06 13:56
Оценка:
Здравствуйте, <Аноним>, Вы писали:

А>Есть примерно такой код:

А>
А>double y_min = -7.0;
А>double y_step = 1.4;
А>for(int i = 0; i <= 10; ++i)
А>{
А>    std::ostringstream oss;
А>    oss << (y_min + i*y_step);
А>    ...
А>}
А>

А>Проблема в том, что при i == 5, в oss в релизе выводится число 8.88178e-16, хотя в дебаге все нормально — выводится 0. (VS 7.1)
А>В чем дело?

очень странно.. я не смог повторить проблемы
... << RSDN@Home 1.1.4 stable SR1 rev. 568>>
 
Подождите ...
Wait...
Пока на собственное сообщение не было ответов, его можно удалить.