Памятка: printf и scanf_s¶
К общим материалам · К лабораторным
Примеры рассчитаны на Visual Studio с компилятором MSVC и используют <stdio.h>.
Имена записываются как printf и scanf_s, без std::. scanf_s доступна не во
всех средах C++; в частности, в обычной среде GCC с glibc её нет. Если используете
другую среду, согласуйте способ ввода с преподавателем.
Форматы для чисел¶
| Тип переменной | Ввод через scanf_s | Вывод через printf |
|---|---|---|
int |
%d |
%d |
float |
%f |
%f |
double |
%lf |
%lf |
Перед переменной при чтении ставится &: программе нужно указать, куда записать число.
При выводе & не ставится.
int count = 0;
float length = 0.0f;
double power = 0.0;
// Это отдельные примеры чтения; каждое чтение проверяется.
if (scanf_s("%d", &count) != 1) {
printf("Input error\n");
return 1;
}
if (scanf_s("%f", &length) != 1) {
printf("Input error\n");
return 1;
}
if (scanf_s("%lf", &power) != 1) {
printf("Input error\n");
return 1;
}
printf("count = %d\n", count);
printf("length = %.3f m\n", length);
printf("power = %.3lf W\n", power);
Для чтения чисел дополнительный аргумент с размером не нужен. Такой аргумент у
scanf_s нужен для ряда символьных форматов, которые здесь не используются.
Тип переменной и спецификатор должны совпадать: %f при чтении double — ошибка.
Правила чтения и возвращаемого значения описаны в документации scanf_s.
Несколько чисел за один раз¶
double a = 0.0;
double b = 0.0;
printf("Enter a and b in meters: ");
if (scanf_s("%lf %lf", &a, &b) != 2) {
printf("Input error\n");
return 1;
}
Сравниваем возвращённое значение с числом ожидаемых записей. Здесь нужны две.
Для трёх переменных ожидалось бы 3. Начальная запись = 0.0 не отменяет проверку чтения.
| Ввод при ожидании двух чисел | Результат чтения |
|---|---|
2 3 |
Прочитаны оба числа |
abc 3 |
Не прочитано ни одного числа |
2 abc |
Прочитано только первое число |
Число прочиталось — допустимо ли оно?¶
Предположим, обе длины должны принадлежать отрезку от 0.001 до 10 м включительно. После успешного чтения проверяем:
if (!(a >= 0.001 && a <= 10.0 &&
b >= 0.001 && b <= 10.0)) {
printf("Data error\n");
return 1;
}
&& означает «и»: все четыре условия должны быть истинны. ! отрицает результат:
внутрь if попадаем, если данные не удовлетворяют всей проверке.
Проверяйте принадлежность разрешённому диапазону целиком; вычисление должно идти
только после подтверждения допустимости всех входов.
Как вывести нужное количество цифр¶
printf("Result = %.3lf W\n", power);
printf("Result = %.10lf W\n", power);
%.3lf выводит double с тремя знаками после точки, %.10lf — с десятью.
Для float аналогично используются %.3f и %.9f. Число после точки в формате
задаёт количество знаков после десятичной точки, а не значащих цифр всего числа.
Без указания точности %f и %lf выводят шесть знаков после точки.
\n переводит строку.
Литеральный знак процента печатается как %%. Форматы описаны в
документации printf.
В материалах курса используем единое соглашение: %f для float, %lf для
double — и при вводе, и при выводе. При чтении это обязательное соответствие типов.
В printf форматы %f и %lf технически равнозначны: float при передаче
автоматически преобразуется в double, а модификатор l не меняет вывод.
Запись %lf для double выбрана для единообразия. Уже потерянные при расчёте
цифры такое преобразование не восстанавливает.
Частые ошибки¶
- В формате чтения указан
%f, а переменная имеет типdouble. - При чтении пропущен
&. - Проверяется
scanf_s(...) == 0, хотя часть значений тоже могла не прочитаться. - Деление выполняется раньше проверки знаменателя.
- В конце формата чтения поставлен
\n, из-за чего программа может ждать продолжения ввода. - Для вещественного результата используется
%d. - Введена десятичная запятая вместо точки.