Обработка чисел на C

#c #programming-languages #numbers #integer #number-formatting

#c #языки программирования #числа #целое #форматирование чисел

Вопрос:

Не мог понять, как обрабатываются числа в C. Кто-нибудь может указать на хороший учебник.

 #include<stdio.h>
main()
{
    printf("%f",16.0/3.0);
}
  

Этот код выдал: 5.333333

Но

 #include<stdio.h>
main()
{
    printf("%d",16.0/3.0);
}
  

Выдал некоторое мусорное значение: 1431655765

Затем

 #include<stdio.h>
main()
{
    int num;
    num=16.0/3.0;
    printf("%d",num);
}
  

Выдает: 5

Затем

 #include<stdio.h>
main()
{
    float num;
    num=16/3;
    printf("%f",num);
}
  

Выдает: 5.000000

Ответ №1:

printf объявляется как

 int printf(const char *format, ...);
  

первым аргументом ( format ) является строка, а остальные могут быть любыми. То, как будут использоваться остальные аргументы, зависит от спецификаторов формата в format . Если у вас есть:

 printf("%d%c", x, y);
  

x будет обрабатываться как int, y будет обрабатываться как char .
Итак,

  printf("%f",16.0/3.0);
  

все в порядке, поскольку вы запрашиваете float удвоить (%f), передать float двойной (16.0/3.0)

 printf("%d",16.0/3.0);
  

вы запрашиваете int(%d), вы передаете float double (double и int имеют разное внутреннее представление) таким образом, битовое представление 16.0 / 3.0 (double) соответствует битовому представлению 1431655765 (int).

  int num;
 num=16.0/3.0;
  

компилятор знает, что вы присваиваете значение int, и преобразует его для вас. Обратите внимание, что это отличается от предыдущего случая.

Комментарии:

1. В "%f", 16.0/3.0 примере строка формата указывает a double и передает a double (константа 16.0 — это double a, и даже если вы использовали float константы типа 16.0f/3.0f , результат был бы повышен до double перед передачей в printf ).

Ответ №2:

Хорошо, первый 1 дает правильное значение, как и ожидалось.

Во-вторых, вы передаете значение float, в то время как оно обрабатывает его как int (отсюда и «%d», который предназначен для отображения типов данных int, немного сложно объяснить, почему, и поскольку кажется, что вы только начинаете, я бы не стал беспокоиться о том, почему «% d» делает это при передаче значения float), читая его неправильно, что дает вам странное значение. (хотя и не мусорное значение).

В-третьих, это делает 16.0 / 3.0 значением int при присвоении его типу данных int, что приведет к 5. Потому что, превращая float в int, он удаляет десятичные дроби независимо от округления.

В четвертом случае правая часть (16/3) обрабатывается как int, потому что у вас нет нуля .0 в конце. Он оценивает, что затем присваивает 5 числу с плавающей точкой. Таким образом, объясняется результат.

Ответ №3:

Это потому, что выбранные вами строки форматирования не соответствуют передаваемым вами аргументам. Я предлагаю ознакомиться с документацией по printf. Если у вас есть «% d», он ожидает целочисленное значение, то способ сохранения этого значения не имеет значения и, вероятно, зависит от компьютера. Если у вас есть «% f», он ожидает число с плавающей запятой, также, вероятно, зависящее от компьютера. Если вы это сделаете:

 printf( "%f", <<integer>> );
  

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

 16.0/3.0 is a float
int num = 16.0/3.0 is a float converted to an int
16/3 is an int
float num = 16/3 is an int converted to a float
  

Вы можете поискать printf документацию в Интернете. Одна страница находится на http://linux.die.net/man/3/printf

Ответ №4:

Вы можете понять числа в C, используя концепцию преобразования типов Implecit.

При вычислении любого выражения соблюдаются очень строгие правила преобразования типов. и ваш ответ о выражении зависит от правил преобразования этого типа.

Если опарандные значения имеют разные типы, «младший» тип автоматически преобразуется в «более высокий» тип перед продолжением операции. результат имеет более высокий тип.

1. Все short и char автоматически преобразуются в int затем

2. если один из операндов является int, а другой — float, то int преобразуется в float, поскольку значение float выше, чем ** int**.

если вы хотите получить больше информации о неявном преобразовании, вам следует обратиться к книге «Программирование на ANSI C» Э. Балагурусами.

Спасибо. Пока: глубокий

Ответ №5:

printf форматирует немного памяти в строку, читаемую человеком. Если вы укажете, что бит памяти следует рассматривать как число с плавающей запятой, вы получите правильное представление числа с плавающей запятой; однако, если вы укажете, что бит памяти следует рассматривать как целое число, и это число с плавающей запятой, вы получите мусор.

Ответ №6:

 printf("%d",16.0/3.0);
  

Результатом 16.0/3.0 является 5.333333, который представлен в формате с плавающей запятой одинарной точности следующим образом

0 | 10101010 | 10101010101010101010101

Если вы прочитаете это как 32-битное целое значение, результат будет 1431655765 .


 num=16.0/3.0;
  

эквивалентно num = (int)(16.0/3.0) . Это преобразует результат значения с плавающей точкой ( 5.33333 ) в целое число( 5 ).


 printf("%f",num);
  

такой же, как printf("%f",(float)num);