Spec-Zone.ru › C

vwprintf, vfwprintf, vswprintf, vwprintf_s, vfwprintf_s, vswprintf_s, vsnwprintf_s

Определено в заголовочном файле <wchar.h>
(1)
int vwprintf( const wchar_t *format, va_list vlist );
(с C95)
(до C99)
int vwprintf( const wchar_t *restrict format, va_list vlist );
(с C99)
(2)
int vfwprintf( FILE* stream, const wchar_t *format, va_list vlist );
(с C95)
(до C99)
int vfwprintf( FILE *restrict stream,
               const wchar_t *restrict format, va_list vlist );
(с C99)
(3)
int vswprintf( wchar_t *buffer, size_t bufsz,
               const wchar_t *format, va_list vlist );
(с C95)
(до C99)
int vswprintf( wchar_t *restrict buffer, size_t bufsz,
               const wchar_t *restrict format, va_list vlist );
(с C99)
int vwprintf_s( const wchar_t *restrict format, va_list vlist);
(4) (с C11)
int vfwprintf_s( FILE * restrict stream,
                 const wchar_t *restrict format, va_list vlist);
(5) (с C11)
int vswprintf_s( wchar_t *restrict buffer, rsize_t bufsz, 
                 const wchar_t * restrict format, va_list vlist);
(6) (с C11)
int vsnwprintf_s( wchar_t *restrict buffer, rsize_t bufsz,
                  const wchar_t *restrict format, va_list vlist);
(7) (с C11)

Загружает данные из местоположений, определенных vlist, преобразует их в эквиваленты широких строк и записывает результаты в различные потоки.

1) Записывает результаты в stdout.
2) Записывает результаты в потоке файла stream.
3) Записывает результаты в широкую строку buffer. Вводится не более bufsz-1 широких символов, за которыми следует нулевой широкий символ. Результирующая широкая строка будет завершена нулевым широким символом, если bufsz не равно нулю.
4-6) То же, что и (1-3), за исключением того, что следующие ошибки обнаруживаются во время выполнения и вызывают текущую установленную функцию обработчика ограничений обработчика ограничений:
  • в format присутствует спецификатор преобразования %n
  • любой из аргументов, соответствующий %s - нулевой указатель
  • format или buffer - нулевой указатель
  • bufsz равно нулю или больше RSIZE_MAX/sizeof(wchar_t)
  • происходят ошибки кодирования в любом из спецификаторов преобразования строк и символов
  • (только для vswprintf_s): строка, подлежащая хранению в buffer (включая заключительный широкий нуль) превысит bufsz
7) То же, что и (6), за исключением того, что результат будет усечен, чтобы уместиться в массиве, на который указывает buffer. Как и во всех функциях с проверкой границ, vwprintf_s, vfwprintf_s, vswprintf_s, и vsnwprintf_s гарантированы только если __STDC_LIB_EXT1__ определено реализацией и если пользователь определит __STDC_WANT_LIB_EXT1__ как целочисленную константу 1 перед включением <stdio.h>.

Параметры

stream - выходной широкий поток для записи
buffer - указатель на широкую строку для записи
bufsz - максимальное количество широких символов для записи
format - указатель на завершающуюся нулём широкую строку, определяющую, как интерпретировать данные
vlist - список переменных аргументов, содержащий данные для печати.


Строка format состоит из обычных широких символов (кроме %), которые без изменений копируются в выходной поток, и спецификаторов преобразования. Каждый спецификатор преобразования имеет следующий формат:

  • вводящий % символ.
  • (необязательно) один или несколько флагов, которые изменяют поведение преобразования:
    • -: результат преобразования выравнивается слева в поле (по умолчанию - справа).
    • +: знак знакового преобразования всегда предшествует результату преобразования (по умолчанию результат предшествует минус только когда он отрицательный).
    • пробел: если результат знакового преобразования не начинается с символа знака или пуст, перед результатом вставляется пробел. Он игнорируется, если присутствует флаг +.
    • #: выполняется альтернативная форма преобразования. См. таблицу ниже для точного эффекта, в противном случае поведение неопределено.
    • 0: для целых и чисел с плавающей точкой, ведущие нули используются для заполнения поля вместо символов пробел. Для целых чисел он игнорируется, если точность явно указана. Для других преобразований использование этого флага приводит к неопределенному поведению. Он игнорируется, если присутствует флаг -.
  • (необязательно) целое значение или *, которое определяет минимальную ширину поля. Результат дополняется символами пробел (по умолчанию), если необходимо, слева, если выравнивание по правому краю, или справа, если выравнивание по левому краю. В случае использования *, ширина определяется дополнительным аргументом типа int, который появляется перед аргументом, подлежащим преобразованию, и аргументом, предоставляющим точность, если она предоставляется. Если значение аргумента отрицательное, оно приводит к указанию флага - и положительной ширине поля (Примечание: это минимальная ширина: значение никогда не усекается).
    • (необязательно) ., за которым следует целое число или *, или ни то, ни другое, что определяет точность преобразования. В случае использования *, точность определяется дополнительным аргументом типа int, который появляется перед аргументом, подлежащим преобразованию, но после аргумента, предоставляющего минимальную ширину поля, если таковой имеется. Если значение этого аргумента отрицательное, оно игнорируется. Если ни число, ни * не используются, точность принимается как ноль. См. таблицу ниже для точного эффекта точности.
    • (необязательно) модификатор длины, который указывает размер аргумента (в сочетании со спецификатором формата преобразования он определяет тип соответствующего аргумента).
    • спецификатор формата преобразования.

Доступны следующие спецификаторы формата:

Преобразование
спецификатор
Описание Ожидаемый
тип аргумента
Модификатор
длины
→
hh

(C99)

h (нет) l ll

(C99)

j

(C99)

z

(C99)

t

(C99)

L
% Записывает литеран %. Полная спецификация преобразования должна быть %%. Н/Д Н/Д Н/Д Н/Д Н/Д Н/Д Н/Д Н/Д Н/Д
c Записывает один символ.

Аргумент сначала преобразуется в wchar_t так, как будто вызывается btowc. Если используется модификатор l, аргумент wint_t сначала преобразуется в wchar_t.

Н/Д Н/Д
int
wint_t
Н/Д Н/Д Н/Д Н/Д Н/Д
s Записывает строку символов

Аргумент должен быть указателем на начальный элемент массива символов, содержащего последовательность многобайтовых символов, начинающуюся в начальном состоянии смены, которая преобразуется в массив широких символов так, как будто вызывается mbrtowc с нулевым начальным состоянием преобразования. Точность указывает максимальное количество широких символов для записи. Если Точность не указана, записываются все широкие символы до, но не включая, первого нулевого терминатора. Если используется спецификатор l, аргумент должен быть указателем на начальный элемент массива wchar_t.

Н/Д Н/Д
char*
wchar_t*
Н/Д Н/Д Н/Д Н/Д Н/Д
d
i
Преобразует целое со знаком в десятичное представление [-]dddd.

Точность определяет минимальное количество цифр. По умолчанию точность равна 1.

Если и преобразованное значение, и точность ​0​ результат преобразования — это отсутствие символов.

signed char
short
int
long
long long
intmax_t
целое со знаком size_t
ptrdiff_t
Н/Д
o Преобразует целое без знака в восьмеричное представление oooo.

Точность определяет минимальное количество цифр. По умолчанию точность равна 1. Если и преобразованное значение, и точность ​0​ результат преобразования — это отсутствие символов. В альтернативной реализации точность увеличивается при необходимости, чтобы записать ведущий ноль. В этом случае, если и преобразованное значение, и точность ​0​, записывается одиночный ​0​.

unsigned char
unsigned short
unsigned int
unsigned long
unsigned long long
uintmax_t
size_t
беззнаковая версия ptrdiff_t
Н/Д
x
X
Преобразует целое без знака в шестнадцатеричное представление hhhh.

Для x преобразования используются символы abcdef.
Для X преобразования используются символы ABCDEF.
Точность определяет минимальное количество цифр. По умолчанию точность равна 1. Если и преобразованное значение, и точность ​0​ результат преобразования — это отсутствие символов. В альтернативной реализации 0x или 0X предшествуют результату, если преобразованное значение отлично от нуля.

Н/Д
u Преобразует целое без знака в десятичное представление dddd.

Точность определяет минимальное количество цифр. По умолчанию точность равна 1. Если и преобразованное значение, и точность ​0​ результат преобразования — это отсутствие символов.

Н/Д
f
F
Преобразует число с плавающей точкой в десятичную запись вида [-]ddd.ddd.

Точность указывает точное количество цифр после десятичной точки. По умолчанию точность равна 6. В альтернативной реализации десятичная точка записывается даже если за ней нет цифр. Для преобразования бесконечности и нечисловых значений см. примечания.

Н/Д Н/Д
double
double(C99)
Н/Д Н/Д Н/Д
long double
e
E
Преобразует число с плавающей точкой в десятичную запись с экспонентой.

Для стиля преобразования e используется запись [-]d.ddde±dd.
Для стиля преобразования E используется запись [-]d.dddE±dd.
Экспонента содержит по крайней мере две цифры, дополнительные цифры используются только при необходимости. Если значение ​0​, экспонента также ​0​. Точность указывает точное количество цифр после десятичной точки. По умолчанию точность равна 6. В альтернативной реализации десятичная точка записывается даже если за ней нет цифр. Для преобразования бесконечности и нечисловых значений см. примечания.

Н/Д Н/Д Н/Д Н/Д Н/Д
a
A

(C99)

Преобразует число с плавающей точкой в шестнадцатеричную запись с экспонентой.

Для стиля преобразования a используется запись [-]0xh.hhhp±d.
Для стиля преобразования A используется запись [-]0Xh.hhhP±d.
Первая шестнадцатеричная цифра не 0 если аргумент — нормализованное число с плавающей точкой. Если значение ​0​, экспонента также ​0​. Точность указывает точное количество цифр после шестнадцатеричной точки. По умолчанию точность достаточна для точного представления значения. В альтернативной реализации десятичная точка записывается даже если за ней нет цифр. Для преобразования бесконечности и нечисловых значений см. примечания.

Н/Д Н/Д Н/Д Н/Д Н/Д
g
G
Преобразует число с плавающей точкой в десятичную или десятичную запись с экспонентой, в зависимости от значения и точности.

Для стиля преобразования g выполняется преобразование со стилем e или f.
Для стиля преобразования G выполняется преобразование со стилем E или F.
Пусть P равно точности, если она отлична от нуля, 6 если точность не указана, или 1 если точность ​0​. Тогда, если преобразование со стилем E имело бы экспоненту X:

  • если P > X ≥ −4, преобразование выполняется со стилем f или F и точностью P − 1 − X.
  • в противном случае, преобразование выполняется со стилем e или E и точностью P − 1.

Если не требуется альтернативное представление, trailing zeros удаляются, а также десятичная точка удаляется, если дробная часть отсутствует. Для преобразования бесконечности и нечисловых значений см. примечания.

Н/Д Н/Д Н/Д Н/Д Н/Д Н/Д
n Возвращает количество записанных символов на данный момент вызовом функции.

Результат записывается в значение, указанное аргументом. Спецификация может не содержать флага, ширины поля или точности.



signed char*
short*
int*
long*
long long*
intmax_t*
знаковый size_t*
ptrdiff_t*
Н/Д
p Записывает определяемую реализацией последовательность символов, определяющую указатель. Н/Д Н/Д void* Н/Д Н/Д Н/Д Н/Д Н/Д Н/Д

Функции преобразования чисел с плавающей запятой преобразуют бесконечность в inf или infinity. Выбор конкретного значения определяется реализацией.

Не-число преобразуется в nan или nan(char_sequence). Выбор конкретного значения определяется реализацией.

Преобразования F, E, G, A выводят INF, INFINITY, NAN соответственно.

Несмотря на то, что %c ожидает аргумент int, безопасно передавать char, из-за повышения целых чисел, которое происходит при вызове вариативной функции.

Правильные спецификации преобразования для типов символов фиксированной ширины (int8_t, и т.д.) определены в заголовке <inttypes.h> (хотя PRIdMAX, PRIuMAX, и т.д. является синонимом для %jd, %ju, и т.д.).

Спецификатор преобразования для записи в память %n является распространённой целью эксплойтов, где строки формата зависят от пользовательского ввода, и не поддерживается семейством функций printf_s с проверкой границ.

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

Если спецификация преобразования неверна, поведение является неопределённым.

Возвращаемое значение

1,4) Количество широких символов, записанных при успешном выполнении, или отрицательное значение при возникновении ошибки.
3) Количество широких символов, записанных при успешном выполнении, или отрицательное значение при возникновении ошибки. Если результирующая строка усекается из-за ограничения bufsz, функция возвращает общее количество символов (без учёта завершающего нулевого широкого символа), которое было бы записано, если бы ограничение не было применено.
2,5) количество широких символов, переданных в поток вывода, или отрицательное значение при ошибке вывода, нарушении ограничений во время выполнения или ошибке кодирования.
6) количество широких символов, записанных в buffer, не считая нулевой широкой символ (который всегда записывается, пока buffer не является нулевым указателем и bufsz не равно нулю и не больше RSIZE_MAX/sizeof(wchar_t) ), или ноль при нарушениях ограничений во время выполнения, и отрицательное значение при ошибках кодирования.
7) количество широких символов, не включая завершающий нулевой символ (который всегда записывается, пока buffer не является нулевым указателем и bufsz не равно нулю и не больше RSIZE_MAX/sizeof(wchar_t) ), которое должно было бы быть записано в buffer если bufsz был пропущен, или отрицательное значение при нарушении ограничений во время выполнения или ошибке кодирования.

Примечания

Все эти функции вызывают va_arg по крайней мере один раз, значение arg неопределено после возвращения. Эти функции не вызывают va_end, и это необходимо сделать вызывающей стороне.

В то время как узкие строки предоставляют vsnprintf, что позволяет определить необходимый размер буфера вывода, нет эквивалента для широких строк (до vsnwprintf_s C11), и для определения размера буфера программе может потребоваться вызвать vswprintf, проверить возвращаемое значение и перевыделить больший буфер, пытаясь снова до тех пор, пока не будет успеха.

vsnwprintf_s, в отличие от vswprintf_s, обрезает результат, чтобы он уместился в массиве, на который указывает buffer, даже если усечение обрабатывается как ошибка большинством функций с проверкой границ.

Пример

#include <stdio.h>
#include <time.h>
#include <locale.h>
#include <stdarg.h>
#include <stddef.h>
#include <wchar.h>
 
void debug_wlog(const wchar_t *fmt, ...)
{
    struct timespec ts;
    timespec_get(&ts, TIME_UTC);
    char time_buf[100];
    size_t rc = strftime(time_buf, sizeof time_buf, "%D %T", gmtime(&ts.tv_sec));
    snprintf(time_buf + rc, sizeof time_buf - rc, ".%06ld UTC", ts.tv_nsec / 1000);
 
    va_list args;
    va_start(args, fmt);
    wchar_t buf[1024];
    int rc2 = vswprintf(buf, sizeof buf / sizeof *buf, fmt, args);
    va_end(args);
 
    if(rc2 > 0)
       wprintf(L"%s [debug]: %ls\n", time_buf, buf);
    else
       wprintf(L"%s [debug]: (string too long)\n", time_buf);
}
 
int main(void)
{
    setlocale(LC_ALL, "");
    debug_wlog(L"Logging, %d, %d, %d", 1, 2, 3);
}

Возможный вывод:

02/20/15 22:12:38.476575 UTC [debug]: Logging, 1, 2, 3

Ссылки

  • Стандарт C11 (ISO/IEC 9899:2011):
    • 7.29.2.5 Функция vfwprintf (стр. 417-418)
    • 7.29.2.7 Функция vswprintf (стр. 419)
    • 7.29.2.9 Функция vwprintf (стр. 420)
    • K.3.9.1.6 Функция vfwprintf_s (стр. 632)
    • K.3.9.1.8 Функция vsnwprintf_s (стр. 633-634)
    • K.3.9.1.9 Функция vswprintf_s (стр. 634-635)
    • K.3.9.1.11 Функция vwprintf_s (стр. 636)
  • Стандарт C99 (ISO/IEC 9899:1999):
    • 7.24.2.5 Функция vfwprintf (стр. 363)
    • 7.24.2.7 Функция vswprintf (стр. 364)
    • 7.24.2.9 Функция vwprintf (стр. 365)

См. также

vprintfvfprintfvsprintfvsnprintfvprintf_svfprintf_svsprintf_svsnprintf_s
(C99)(C11)(C11)(C11)(C11)
печатает форматированный вывод в stdout, поток файла или буфер
используя список переменных аргументов
(функция)
wprintffwprintfswprintfwprintf_sfwprintf_sswprintf_ssnwprintf_s
(C95)(C95)(C95)(C11)(C11)(C11)(C11)
печатает форматированный вывод широких символов в stdout, поток файла или буфер
(функция)
Документация C++ для vwprintf, vfwprintf, vswprintf

© cppreference.com
Licensed under the Creative Commons Attribution-ShareAlike Unported License v3.0.
https://en.cppreference.com/w/c/io/vfwprintf

Spec-Zone.ru

Настройки Оффлайн Что нового Помощь О нас
Spec-Zone .ru
спецификации, руководства, описания, API