Использование спецификатора ширины печати с переменной целочисленного типа с фиксированной шириной - PullRequest
1 голос
/ 08 октября 2019

w - это параметр, который определяет ширину вывода, p - это число, которое должно быть напечатано в восьмеричной системе. Обе переменные должны быть целыми числами фиксированной ширины (uint32_t) (этозадание для моего класса программирования). Я гуглил, что могу использовать макросы PRIo32 (inttypes.h) для печати int32_t в восьмеричном виде, но я не смог найти макросов для спецификатора ширины. Поэтому, когда я пытаюсь:

printf("%*" PRIo32 "\n", w, p);

я получаю эту ошибку в тестовой системе

ошибка: спецификатор ширины поля '*' ожидает аргумент типа 'int', но аргумент 2имеет тип 'int32_t' [-Werror = format =]

Есть ли макросы, которые решают эту проблему? Или я должен попробовать что-то еще?

1 Ответ

0 голосов
/ 08 октября 2019

Приведите ширину uint32_t к int. @ Камил Цук

// printf("%*" PRIo32 "\n", w, p);
printf("%*" PRIo32 "\n", (int) w, p);

При необходимости выявлять экстремальные случаи

assert(w <= INT_MAX);
printf("%*" PRIo32 "\n", (int) w, p);

Никаких предположений о int диапазоне не требуется.


Глубже

Обратите внимание, что один отпечаток с огромной шириной может вызвать проблемы из-за ограничений по окружающей среде . Ширина выше 4095 или около того может просто не работать.

Ограничения среды Число символов, которое может быть получено при любом одном преобразовании, должно быть не менее 4095. C17dr § 7.21.6.1 15

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

uint32_t w2 = w;
while (w2 > 100) {
  w2--;
  putchar(' ');
}
printf("%*" PRIo32 "\n", (int) w2, p);
...