Поплавки не добавляются? - PullRequest
       20

Поплавки не добавляются?

0 голосов
/ 11 октября 2018

Я пытаюсь разработать программу для расчета и отображения количества секунд, пока текущее население не достигнет 8 миллиардов.Я думаю, что моя логика правильна, но мой цикл while зацикливается бесконечно, и я не могу понять, почему.

Я привык к C ++, но я впервые пишу на C, поэтому мне интересно,есть некоторая синтаксическая проблема, которую я пропускаю.

// Program to calculate population increase
// to see how many seconds from now
// the population will hit 8 billion

#include <stdio.h>
#include <math.h>

int main()
{
    float currentPop = 7600000000.0;
    float increasePerSec = 2.5;
    int secondCount = 0;

    printf("Counting...\n");

    while (currentPop < 8000000000.01)
    {
        currentPop += increasePerSec;
        secondCount++;
    }
    printf("It will be %f seconds from now.\n",secondCount);

    return 0;
}

Кажется, что проблема существует в этой строке:

currentPop += increasePerSec;

, потому что значение всегда остается на уровне 7,6 миллиарда.На всякий случай я попробовал:

currentPop = currentPop + increasePerSec;

, но без изменений в результате.

Ответы [ 3 ]

0 голосов
/ 11 октября 2018

В наиболее часто используемом формате для float, базовом 32-битном формате IEEE-754, представимые значения около 7600000000 равны 7599999488, 7600000000 и 7600000512. Это связано с тем, что 32-битный формат использует только 24 бита дляЗначение и (дробная часть).Для представления 7600000000 показатель степени должен быть установлен таким образом, чтобы старший бит значенияи представлял 4294967296 (2 32 ), что означает, что младший бит представляет 512 (2 9 ).Таким образом, приращения к представимым числам в этой точке происходят в единицах 512.

Когда вы добавляете 2,5 к 7600000000, математический результат, 7600000002,5, округляется до ближайшего представимого значения, поэтому окончательный результат составляет 7600000000.

В наиболее часто используемом формате для double имеется 53 бита для значения, так что числа с половинами (2 -1 ) могут быть представлены вплоть до 2 53 (9007199254740992).

Примечание. В этом ответе предполагается, что используются общие форматы.Если требуется большая мобильность, реализация C предоставляет информацию о своей информации с плавающей точкой в ​​<float.h>.Эта информация может использоваться для проверки того, обеспечивают ли форматы float или double достаточную точность.

0 голосов
/ 11 октября 2018

Предполагая, что float является типом с плавающей запятой IEEE754 одинарной точности, он может содержать до 8 десятичных знаков точности.Таким образом, добавление значения от 2,5 до 7600000000 выходит за рамки точности, которую может содержать этот тип, что означает, что результатом будет 7600000000. Таким образом, у вас есть бесконечный цикл.

Измените тип данных на double, чтоимеет гораздо больше точности.Затем цикл должен завершиться.

Кроме того, вы используете спецификатор формата %f для печати secondCount, который является целым числом.Вместо этого вы должны использовать %d.

0 голосов
/ 11 октября 2018

Так же, как дополнение, вы можете проверить значение sizeof (float) на вашем компьютере, потому что максимальное значение, которое может быть сохранено в нем, может быть меньше 7600000000.0 или 8000000000.01

...