2014-07-03 3 views
0

Первой ситуациейLoop с плавающей точкой итерации

for (int i = 0 ; i <=2 ; i++) 
{ 
    cout << i << endl ; 
} 

выхода:

1 
2 

Второй ситуация

for (float i = 0 ; i <= 2 ; i+=.2) 
{ 
    cout << i << endl; 
} 

выходной

1 
1.2 
1.4 
1.6 
1.8 

Вопрос заключается в том, почему во второй ситуации он не брал 2 даже я сказал (< =) и самое смешное, если я удалить = выход будет даже то же самое?

Сдерживает я должен использовать поплавок DataType и я хочу использовать < = Оператор

+3

'2.0' не равно' 2'! – haccks

+1

@haccks: 2.0/2.0f * is * равно 2, проблема 0.2f! = 0.2 (математически) и '0.2f + 0.2f + 0.2f + 0.2f + 0.2f! = 1'. @ H.Scrope: представление с плавающей точкой не совсем точно, поэтому после ваших добавлений вы получаете число, которое когда-либо было немного меньше 2. Вы могли бы сказать '<2.1', чтобы решить вашу проблему, так как накопленная ошибка будет быть намного меньше (около 15-й цифры). –

+0

Фактически, 'float' является точным. Но вы можете использовать 'float' для' int' для сравнения. – YaleCheung

ответ

0

Вы не можете сравнить поплавковые или двойные переменные, используя == из-за возможных ошибок округлого арифметического округления. Вы должны использовать epsilon.

const float EPSILON = 0.00001f; 
for (float f = 0.0f; EPSILON > std::fabs(f - 2.0f); f += 0.2f) 
{ 
std::cout << f << std::endl; 
} 

Также попробуйте использовать lireral f при использовании типа поплавка (float my_float = 12.4f;).

+2

Я не согласен с тем, что использование epsilon - это путь вперед. Это нормально при некоторых обстоятельствах (например, приведенный пример), но может быть неуместным для очень больших или очень маленьких (<1,0) номеров. Опять же, я ссылаюсь на [Bruce Dawson] (http://randomascii.wordpress.com/2012/02/25/comparing-floating-point-numbers-2012-edition/), который хорошо сравнивает сравнение, а также объясняет. – icabod

+0

1) условие iverted: Условие должно быть верным, чтобы продолжить цикл. То, что вы написали, является условием остановки цикла. 2) Это сработает, если вы захотите перейти на 100.0f вместо 2.0f – fjardon

1

Поскольку 0,2 не подходит точно в обращении и вы набираете с плавающей точкой ошибки в ваш цикл. На моем компьютере, накапливающемся 10 раз 0,2, равно 2.38419e-07 выше 2.0f

+0

thanQ я получил его. –

+0

Точнее, это математически не может соответствовать точно в представлении base-2. Как то, как «1/3» не может точно вписываться в представление base-10 (это 0,3333333 .....) –

Смежные вопросы