Есть ли в стандартной библиотеке C ++ шаблонный геттер для спецификатора преобразования printf?

Как мы все знаем, если по какой-то причине вы printf() что-то, а не поток (это редко, но иногда может случиться), вам нужно указать соответствующий спецификатор формата (d для подписанного int, u для неподписанных и т. д. и т. д.). Теперь, так как printf() является частью стандартной библиотеки C ++, а не просто наследием C, я надеюсь, что что-то будет

template <typename T>
const std::string format_specifier;

Что позволит, скажем:

template <typename Foo>
void bar(const Foo& my_foo) {
printf(format_specifier<Foo>, my_foo);
}

Стандартная библиотека содержит что-то подобное?

Заметки:

  • Пожалуйста, не предлагайте использовать std::coutКонечно, это то, что вы должны сделать по умолчанию. Я спросил о функции, которая является частью стандартной библиотеки; если бы он был удален из него, вы могли бы сказать: «это никогда не должно использоваться, поэтому ваш вопрос не имеет значения».

4

Решение

Первоначально я написал это как комментарий, так как это казалось слишком коротким.

Краткий ответ — «нет», так как стандарт C ++ не определяет никаких таких возможностей.

Заданы свойства функций, которые унаследованы от стандартной библиотеки C по причинам обратной совместимости (без перегрузки, допускается как в глобальном пространстве имен, так и в пространстве имен std и т. Д.), А также способ использования C ++. iostream занятия поощряются, я был бы удивлен, если бы такая функция когда-либо стала стандартизированной.

3

Другие решения

Он не существует в библиотеке C ++ по некоторым причинам.

Во-первых, если вы хотите, чтобы C ++ помог вам найти правильный способ вывода объекта, C ++ предлагает вам инжекторы для stream классы. Поток выбирает подходящий конвертер и может быть изменен с помощью манипуляторов — его даже можно проинструктировать, как распечатать произвольный объект путем перегрузки ostream& operator << (ostream&, const T&),

Но с другой стороны, строка формата printf может использоваться на других языках (Python, Java), и для старых программистов, которые ее использовали, гораздо проще использовать, чем манипуляторы io. Но его можно использовать в довольно сложных строках, смешивающих константные метки и переменные разных типов:

printf("Operation %-*s : %10.2f$ %2d%/02d\n", size, lib, val, dat->mday, dat->mon + 1);

Я не могу себе представить способ легко построить эту строку (и она не использует чередовать варианты (#))

И так как он существует в основном для совместимость причины — в конце концов, почти вся стандартная библиотека C пригодна для использования из C ++ — я не могу себе представить, почему это потребует дальнейшей интеграции.

3

Нет, но вы могли бы написать это достаточно легко, например:

template<typename T>
char const *format_specifier();

template<> inline char const *format_specifier<int>() { return "%d"; }

// ... in function
int d = 5;
printf(format_specifier<decltype(d)>, d);

Это довольно грубо, хотя ИМХО и все еще подвержено ошибкам. Вероятно, почему этого нет в стандартной библиотеке.

Лучшее решение, которое использует форматирование в стиле printf, было бы кодировать:

my_printf("bla % bla % bla", arg1, arg2, arg3);

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

2
По вопросам рекламы [email protected]