Форматированный ввод и вывод

Example

The following example shows the usage of printf() function.

#include <stdio.h>

int main () {
   int ch;

   for( ch = 75 ; ch <= 100; ch++ ) {
      printf("ASCII value = %d, Character = %c\n", ch , ch );
   }

   return(0);
}

Let us compile and run the above program to produce the following result −

ASCII value = 75, Character = K
ASCII value = 76, Character = L
ASCII value = 77, Character = M
ASCII value = 78, Character = N
ASCII value = 79, Character = O
ASCII value = 80, Character = P
ASCII value = 81, Character = Q
ASCII value = 82, Character = R
ASCII value = 83, Character = S
ASCII value = 84, Character = T
ASCII value = 85, Character = U
ASCII value = 86, Character = V
ASCII value = 87, Character = W
ASCII value = 88, Character = X
ASCII value = 89, Character = Y
ASCII value = 90, Character = Z
ASCII value = 91, Character = 
ASCII value = 94, Character = ^
ASCII value = 95, Character = _
ASCII value = 96, Character = `
ASCII value = 97, Character = a
ASCII value = 98, Character = b
ASCII value = 99, Character = c
ASCII value = 100, Character = d

stdio_h.htm

Previous Page
Print Page

Next Page  

The printf family of functions

There are a number of variants of functions. Here is a quick guide:

F# function C# equivalent Comment
and and Functions starting with “print” write to standard out.
and and Functions starting with “eprint” write to standard error.
and and Functions starting with “fprint” write to a TextWriter.
Functions starting with “sprint” return a string.
Functions starting with “bprint” write to a StringBuilder.
, , and No equivalent Functions that accept a continuation. See next section for a discussion.

All of these except and the family are automatically available (via Microsoft.FSharp.Core.ExtraTopLevelOperators).
But if you need to access them using a module, they are in the module.

The usage of these should be obvious (except for the family, of which more below).

A particularly useful technique is to use partial application to “bake in” a TextWriter or StringBuilder.

Here is an example using a StringBuilder:

And here is an example using a TextWriter:

More on partially applying printf

Note that in both cases above, we had to pass a format parameter when creating the partial application.

That is, we had to do:

rather than the point-free version:

This stops the compiler complaining about an incorrect type. The reason why is non-obvious. We briefly mentioned the above as the first parameter to . It turns out that is not actually a particular function, like ,
but rather a generic function that has to be parameterized with a TextWriterFormat (or the similar StringFormat) in order to become “real”.

So, to be safe, it is best to always pair a with a format parameter, rather than being overly aggressive with the partial application.

Conforming To

The fprintf(), printf(), sprintf(), vprintf(), vfprintf(), and vsprintf() functions conform to C89 and C99. The
snprintf() and vsnprintf() functions conform to C99.

Concerning the return value of snprintf(), SUSv2 and C99 contradict each other: when snprintf() is called with size=0 then SUSv2
stipulates an unspecified return value less than 1, while C99 allows str to be NULL in this case, and gives the return value (as always) as the number
of characters that would have been written in case the output string has been large enough.

Linux libc4 knows about the five C standard flags. It knows about the length modifiers h, l, L, and the conversions c, d,
e, E, f, F, g, G, i, n, o, p, s, u, x, and X, where F
is a synonym for f. Additionally, it accepts D, O, and U as synonyms for ld, lo, and lu. (This is bad, and
caused serious bugs later, when support for %D disappeared.) No locale-dependent radix character, no thousands’ separator, no NaN or infinity, no «%m$»
and «*m$».

Linux libc5 knows about the five C standard flags and the ‘ flag, locale, «%m$» and «*m$». It knows about the length modifiers h, l, L,
Z, and q, but accepts L and q both for long double and for long long int (this is a bug). It no longer recognizes
F, D, O, and U, but adds the conversion character m, which outputs strerror(errno).

glibc 2.0 adds conversion characters C and S.

glibc 2.1 adds length modifiers hh, j, t, and z and conversion characters a and A.

glibc 2.2 adds the conversion character F with C99 semantics, and the flag character I.

Parameters

  • str − This is the pointer to an array of char elements where the resulting C string is stored.

  • format − This is the String that contains the text to be written to buffer. It can optionally contain embedded format tags that are replaced by the values specified in subsequent additional arguments and formatted as requested. Format tags prototype: %specifier, as explained below −

Sr.No. Specifier & Output
1

c

Character

2

d or i

Signed decimal integer

3

e

Scientific notation (mantissa/exponent) using e character

4

E

Scientific notation (mantissa/exponent) using E character

5

f

Decimal floating point

6

g

Uses the shorter of %e or %f.

7

G

Uses the shorter of %E or %f

8

o

Signed octal

9

s

String of characters

10

u

Unsigned decimal integer

11

x

Unsigned hexadecimal integer

12

X

Unsigned hexadecimal integer (capital letters)

13

p

Pointer address

14

n

Nothing printed

15

%

Character

Sr.No. Flags & Description
1

Left-justify within the given field width; Right justification is the default (see width sub-specifier).

2

+

Forces to precede the result with a plus or minus sign (+ or -) even for positive numbers. By default, only negative numbers are preceded with a -ve sign.

3

(space)

If no sign is going to be written, a blank space is inserted before the value.

4

#

Used with o, x or X specifiers the value is preceded with 0, 0x or 0X respectively for values different than zero. Used with e, E and f, it forces the written output to contain a decimal point even if no digits would follow. By default, if no digits follow, no decimal point is written. Used with g or G the result is the same as with e or E but trailing zeros are not removed.

5

Left-pads the number with zeroes (0) instead of spaces, where padding is specified (see width sub-specifier).

Sr.No. Width & Description
1

(number)

Minimum number of characters to be printed. If the value to be printed is shorter than this number, the result is padded with blank spaces. The value is not truncated even if the result is larger.

2

*

The width is not specified in the format string, but as an additional integer value argument preceding the argument that has to be formatted.

Sr.No. .precision & Description
1

.number

For integer specifiers (d, i, o, u, x, X) − precision specifies the minimum number of digits to be written. If the value to be written is shorter than this number, the result is padded with leading zeros. The value is not truncated even if the result is longer. A precision of 0 means that no character is written for the value 0. For e, E and f specifiers − this is the number of digits to be printed after the decimal point. For g and G specifiers − This is the maximum number of significant digits to be printed. For s − this is the maximum number of characters to be printed. By default all characters are printed until the ending null character is encountered. For c type − it has no effect. When no precision is specified, the default is 1. If the period is specified without an explicit value for precision, 0 is assumed.

2

.*

The precision is not specified in the format string, but as an additional integer value argument preceding the argument that has to be formatted.

Sr.No. Length & Description
1

h

The argument is interpreted as a short int or unsigned short int (only applies to integer specifiers: i, d, o, u, x and X).

2

l

The argument is interpreted as a long int or unsigned long int for integer specifiers (i, d, o, u, x and X), and as a wide character or wide character string for specifiers c and s.

3

L

The argument is interpreted as a long double (only applies to floating point specifiers − e, E, f, g and G).

additional arguments − Depending on the format string, the function may expect a sequence of additional arguments, each containing one value to be inserted instead of each %-tag specified in the format parameter (if any). There should be the same number of these arguments as the number of %-tags that expect a value.

Модификаторы длины

Эти модификаторы пишутся между знаком % и символом, обозначающим тип. Например, %lld. Эти модификаторы используются для того, чтобы вывести значения типов short int, long int, long double и т.д. и уже упоминались раньше.

hh Используется для значения типа char вместе с символами d, i, u для вывода в виде десятичного числа, соотвветствующего его ASCII-коду.
h Используется для значения типа short int или unsigned short int вместе с модификаторами d, i, u.
l

Используется для значения типа long int или unsigned long int вместе с модификаторами d, i, u.

Используется для значения типа double вместе с модификаторами e, f, g.

ll Используется для значения типа long long int или unsigned long long int вместе с модификаторами d, i, u.
L Используется для значения типа long double вместе с модификаторами e, f, g. Не следует использовать в Windows.

Ширина поля вывода

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

Если перед шириной поля поставить цифру 0, например, «%010d», то число будет дополняться слева не пробелами, а нулями. Это удобно, например, для вывода времени в формате hh:mm, что можно сделать, например, так:

printf(«%02d:%02d», h, m);

Если перед шириной поля поставить знак «-«, то число будет дополняться пробелами не слева, а справа (сначала выводится число, потом — дополнительные пробелы до заполнения всего поля).

Также вместо ширины поля вывода можно указать символ «*» (звездочка), тогда значение ширины поля вывода нужно передать в качестве дополнительного параметра. Например, запись:

printf(«%*d», n, a);

означает вывести значение переменной a используя поле шириной n символов.

Точность вывода действительных чисел

По умолчанию действительные числа выводятся с 6 знаками после точки, при этом числа в экспоненциальной форме выводятся в виде одной цифры, точки и 6 цифр после точки (и показателя степени).

Для изменения точности вывода действительных чисел в форматной строке указывается символ точки (‘.’) и после нее число — количество выводимых знаков после точки. Например, так:

printf(«%.10lf», x);

Вывод целых чисел со знаком +/-

Если при выводе целого числа в форматной строке задать символ «+», то положительные числа будут выводиться с обязательным знаком «+» перед ними.

Большинство перечисленных выше параметров комбинируются друг с другом. Например, такая строка:

printf(«%+020lld», n);

означает вывод числа типа long long, со знаком «+» или «-» перед числом, с добавлением нулей таким образом, что общее число выводимых символов будет не меньше 20.

Example

To print Pi to five decimal places:

To print a date and time in the form «Sunday, July 3, 10:02», where weekday and month are pointers to strings:
Many countries use the day-month-year order. Hence, an internationalized version must be able to print the arguments in an order specified by the
format:
where format depends on locale, and may permute the arguments. With the value:
"%1$s, %3$d. %2$s, %4$d:%5$.2d\n"
one might obtain «Sonntag, 3. Juli, 10:02».

To allocate a sufficiently large string and print into it (code correct for both glibc 2.0 and glibc 2.1):

If truncation occurs in glibc versions prior to 2.0.6, this is treated as an error instead of being handled gracefully.

How to specify a format

The “%” format specifications are quite similar to those used in C, but with some special customizations for F#.

As with C, the characters immediately following the have a specific meaning, as shown below.

We’ll discuss each of these attributes in more detail below.

Formatting for dummies

The most commonly used format specifiers are:

  • for strings
  • for bools
  • for ints
  • for floats
  • for pretty-printing tuples, records and union types
  • for other objects, using

These six will probably meet most of your basic needs.

Controlling width and alignment

When formatting fixed width columns and tables, you need to have control of the alignment and width.

You can do that with the “width” and “flags” options.

  • , . A number sets the width of the value
  • , . A star sets the width of the value dynamically (from an extra parameter just before the param to format)
  • , . A hyphen left justifies the value.

Here are some examples of these in use:

Formatting integers

There are some special options for basic integer types:

  • or for signed ints
  • for unsigned ints
  • and for lowercase and uppercase hex
  • for octal

Here are some examples:

The specifiers do not enforce any type safety within the integer types. As you can see from the examples above, you can pass a signed int to an unsigned specifier without problems.
What is different is how it is formatted. The unsigned specifiers treat the int as unsigned no matter how it is actually typed.

Note that is not a basic integer type, so you must format it with or .

You can control the formatting of signs and zero padding using the flags:

  • pads with zeros
  • shows a plus sign
  • shows a blank in place of a plus sign

Here are some examples:

Formatting floats and decimals

For floating point types, there are also some special options:

  • for standard format
  • or for exponential format
  • or for the more compact of and .
  • for decimals

Here are some examples:

The decimal type can be used with the floating point specifiers, but you might lose some precision.
The specifier can be used to ensure that no precision is lost. You can see the difference with this example:

You can control the precision of floats using a precision specification, such as and .
For the and specifiers, the precision affects the number of digits after the decimal point, while for it is the number of digits in total.
Here’s an example:

The alignment and width flags work for floats and decimals as well.

Custom formatting functions

There are two special format specifiers that allow to you pass in a function rather than just a simple value.

  • expects a function that outputs some text with no input
  • expects a function that outputs some text from a given input

Here’s an example of using :

Obviously, since the callback function takes no parameters, it will probably be a closure that does reference some other value.
Here’s an example that prints random numbers:

For the specifier, the callback function takes an extra parameter. That is, when using the specifier, you must pass in both a function and a value to format.

Here’s an example of custom formatting a tuple:

Date formatting

There are no special format specifiers for dates in F#.

If you want to format dates, you have a couple of options:

  • Use to convert the date into a string, and then use the specifier
  • Use a custom callback function with the specifier as described above

Here are the two approaches in use:

Which approach is better?

The with is easier to test and use, but it will be less efficient than writing directly to a TextWriter.

printf gotchas

There are a couple of “gotchas” to be aware of when using .

First, if there are too few parameters, rather than too many, the compiler will not complain immediately, but might give cryptic errors later.

The reason, of course, is that this is not an error at all; is just being partially applied!
See the discussion of partial application if you are not clear of why this happens.

Another issue is that the “format strings” are not actually strings.

In the .NET formatting model, the formatting strings are normal strings, so you can pass them around, store them in resource files, and so on.
Which means that the following code works fine:

On the other hand, the “format strings” that are the first argument to are not really strings at all, but something called a .
Which means that the following code does not work:

The compiler does some magic behind the scenes to convert the string constant into the appropriate TextWriterFormat.
The TextWriterFormat is the key component that “knows” the type of the format string, such as or , which in turn allows
to be typesafe.

If you want to emulate the compiler, you can create your own TextWriterFormat value from a string using the type in the module.

If the format string is “inline”, the compiler can deduce the type for you during binding:

But if the format string is truly dynamic (e.g. stored in a resource or created on the fly), the compiler cannot deduce the type for you,
and you must explicitly provide it with the constructor.

In the example below, my first format string has a single string parameter and returns a unit, so I have to specify as the format type.
And in the second case, I have to specify as the format type.

I won’t go into detail on exactly how TextWriterFormat` work together right now – just be aware that is not just a matter of simple format strings being passed around.

Finally, it’s worth noting that and family are not thread-safe, while and family are.

If you find this site useful, you can download it as a ebook/PDF here.

ПримечанияRemarks

Функция _snprintf_s форматирует и сохраняет количество символов в буфере и добавляет завершающее значение null.The _snprintf_s function formats and stores count or fewer characters in buffer and appends a terminating null. Каждый аргумент (при его наличии) преобразуется и выводится в соответствии с соответствующей спецификацией формата в формате.Each argument (if any) is converted and output according to the corresponding format specification in format. Форматирование согласуется с семейством функций printf . см. раздел синтаксис спецификации формата: функции printf и wprintf.The formatting is consistent with the printf family of functions; see Format Specification Syntax: printf and wprintf Functions. Если производится копирование между перекрывающимися строками, поведение не определено.If copying occurs between strings that overlap, the behavior is undefined.

Если параметр Count имеет значение _TRUNCATE, то _snprintf_s записывает столько строк, сколько будет помещаться в буфер , оставляя место для завершающего null.If count is _TRUNCATE, then _snprintf_s writes as much of the string as will fit in buffer while leaving room for a terminating null. Если вся строка (с завершающим значением NULL) помещается в буфер, _snprintf_s возвращает количество записанных символов (не включая завершающее значение null); в противном случае _snprintf_s возвращает значение-1, чтобы указать, что произошло усечение.If the entire string (with terminating null) fits in buffer, then _snprintf_s returns the number of characters written (not including the terminating null); otherwise, _snprintf_s returns -1 to indicate that truncation occurred.

Важно!

Убедитесь, что format не является строкой, определяемой пользователем.Ensure that format is not a user-defined string.

_snwprintf_s — это версия _snprintf_sдля расширенных символов; аргументы-указатели для _snwprintf_s являются строками расширенных символов._snwprintf_s is a wide-character version of _snprintf_s; the pointer arguments to _snwprintf_s are wide-character strings. Обнаружение ошибок кодирования в _snwprintf_s может отличаться от обнаруженных в _snprintf_s.Detection of encoding errors in _snwprintf_s might differ from that in _snprintf_s. _snwprintf_s, например swprintf_s, записывает выходные данные в строку, а не в назначение файлатипа._snwprintf_s, like swprintf_s, writes output to a string rather than to a destination of type FILE.

Версии этих функций с суффиксом _l идентичны за исключением того, что они используют переданный параметр языкового стандарта вместо локали текущего потока.The versions of these functions with the _l suffix are identical except that they use the locale parameter passed in instead of the current thread locale.

В C++ использование данных функций упрощено наличием шаблонных перегрузок; перегруженные методы могут автоматически определять длину буфера (что исключает необходимость указания аргумента с размером буфера), а также они могут автоматически заменять более старые, незащищенные функции их новыми безопасными аналогами.In C++, using these functions is simplified by template overloads; the overloads can infer buffer length automatically (eliminating the need to specify a size argument) and they can automatically replace older, non-secure functions with their newer, secure counterparts. Дополнительные сведения см. в разделе Secure Template Overloads.For more information, see Secure Template Overloads.

Сопоставления подпрограмм обработки обычного текстаGeneric-Text Routine Mappings

Процедура Tchar.hTchar.h routine _UNICODE и _MBCS не определены_UNICODE and _MBCS not defined _MBCS определено_MBCS defined _UNICODE определено_UNICODE defined
_sntprintf_s_sntprintf_s _snprintf_s_snprintf_s _snprintf_s_snprintf_s _snwprintf_s_snwprintf_s
_sntprintf_s_l_sntprintf_s_l _snprintf_s_l_snprintf_s_l _snprintf_s_l_snprintf_s_l _snwprintf_s_l_snwprintf_s_l

Именование функций семейства[править]

Все функции имеют в имени основу printf. Префиксы перед именем функции означают:

  • v (vprintf, vsnprintf и т.д.) — функция вместо переменного числа параметров принимает список аргументов va_list.
  • f (fprintf, vfprintf) — вывод результата в передаваемый через параметр функции поток, вместо стандартного вывода.

s (sprintf, snprintf, vsprintf, vspnprintf) — запись результата в строку (буфер в памяти), а не поток.

n (snprintf, vnsprintf) — наличие параметра, ограничивающего максимальное количество символов для записи результата (используется только вместе с префиксом s). В Maple функция nprintf аналогична sprintf, но возвращает не текстовую строку, а имя.

w, перед остальными префиксами (wsnprintf, wvsnprintf) — использующийся фирмой Microsoft префикс для реализаций семейства функций sprintf в операционных системах Windows.

w, после остальных префиксов (fwprintf, swprintf, wprintf) — функция использует многобайтовую кодировку (wchar_t) вместо обычных строк. (при этом функция swprintf не имеет префикса «n», хотя и принимает параметр, ограничивающий размер результирующей строки).

a (asprintf, vasprintf) — расширения GNU; функции аналогичные sprintf/vsprintf, но выделяющие достаточный объём памяти с помощью malloc для форматированной строки. Вместо указателя на строку эти функции принимают указатель на указатель на строку, освобождение памяти производит вызвавшая функция.

Добавить комментарий

Ваш адрес email не будет опубликован. Обязательные поля помечены *

Adblock
detector