Int значения являются значениями с плавающей точкой, поэтому, если вы хотите различить guish между значениями с плавающей точкой, которые также являются целыми числами, и значениями с плавающей запятой, которые не являются целыми числами, вы должны сначала попробовать его как int. Кроме того, scanf вернет успех, если какой-либо префикс совпадает со спецификатором, и проигнорирует дополнительные элементы в конце строки. Если вы этого не хотите, вам нужно использовать% n и убедиться, что он поглотил всю строку. Таким образом, в результате вы получите:
float checkf;
int checki, len;
if (sscanf(argv[1], "%d %n", &checki, &len) >= 1 && argv[1][len] == 0) {
printf("%s is an int\n", argv[i]);
} else if (sscanf(argv[i], "%f %n", &checkf, &len) >= 1 && argv[i][len] == 0) {
printf("%s is a float\n", argv[i]);
} else {
printf("%s is neither an int nor a float\n", argv[i]);
}
%n
в строке формата, заставляя scanf сообщать, сколько символов ввода было использовано до этой точки в формате, и помещать его в конце Формат позволяет нам проверить, что конец формата совпадает с концом строки, и что на входе нет других искажений. В этом случае ввод с плавающей запятой, такой как 2.5
, выглядит как целое число 2
, за которым следует дополнительная строка .5
для первого вызова scanf, поэтому scanf будет успешным (возврат 1), но len будет установлен на .
(поэтому argv[i][len]
будет '.'
, а не 0)