Signature
printf(string $format, mixed ...$values): intPurpose
printf() builds a string from a template and sends it straight to the output. The template holds ordinary text plus placeholders called conversion specifications. Each placeholder says which value to insert and how to present it: padded, rounded, in hexadecimal, and so on. Use it when layout matters, such as aligned columns, fixed decimals or zero-padded codes. If you need the result as a string instead of printing it, use sprintf().
Signature
Parameters
$format is the template. Everything except % is copied unchanged. A placeholder follows this shape:
%[argnum$][flags][width][.precision]specifier
- argnum: an integer followed by
$, selecting which argument to use. This lets you reuse or reorder values. - flags:
-left-justifies,+always shows a sign,0pads with zeros, a space pads with spaces (the default), and'xpads with the characterx. - width: the minimum number of characters. A
*takes the width from an extra integer argument. - precision: a period plus a number. For
f,F,eandEit is the digits after the decimal point (6 by default). Forsit is a maximum length that truncates the string. - specifier: the conversion type. Common ones are
d(signed integer),u(unsigned),s(string),f/F(float),e/E(scientific),b,o,x,X(binary, octal, hex),c(character from a code) and%(a literal percent sign).
...$values holds the arguments, in the order the placeholders consume them. Values are coerced to the type the specifier needs.
Return value and failure cases
The function returns an int: the length of the string it output. Since PHP 8.0 it no longer returns false. Problems throw exceptions instead:
ValueErrorwhen no arguments are given, or when a width or precision is out of range.ArgumentCountErrorwhen the template needs more arguments than you supplied.
Example 1: output and return value
The return value counts the characters that were printed, including the newline in the template.
$length = printf("%s has %d items\n", "Cart", 3);
echo $length, "\n";Cart has 3 items 17
Example 2: aligned columns
A width with - left-aligns text. A width with a precision gives right-aligned fixed decimals. The 0 flag pads the quantity with zeros.
$rows = [["Pen", 1.5, 3], ["Notebook", 12.25, 10]];
foreach ($rows as [$name, $price, $qty]) {
printf("%-10s|%8.2f|%03d\n", $name, $price, $qty);
}Pen | 1.50|003 Notebook | 12.25|010
Example 3: argument numbers, literal percent, padding and hex
Argument numbers let the template use values out of order. In a double-quoted PHP string, write the dollar sign as \$ so PHP does not try to interpolate a variable.
printf("%2\$s scored %1\$d%% (%3\$s)\n", 87, "Ana", "pass");
printf("#%02X%02X%02X\n", 255, 128, 0);
printf("[%'*8s]\n", "php");
printf("[%5.1s]\n", "hello");Ana scored 87% (pass) #FF8000 [*****php] [ h]
Edge cases
%cignores padding and width, so it is only useful for single characters.- Width and precision count bytes, not visible characters. Padding or truncating multibyte text such as UTF-8 can cut a character in half or misalign output. Use multibyte-aware functions for that text.
%ushows a negative integer as its large unsigned equivalent.%frespects the current locale, while%Fdoes not. Prefer%Fwhen the decimal separator must always be a period.%dconverts its argument to an integer, so a float loses its fractional part and a non-numeric string becomes0.- With the
0flag on a string placeholder, zeros are added to the right side when you combine it with left-justification. - Mixing numbered and unnumbered placeholders in one template is easy to get wrong. Choose one style per template.
Common mistakes
- Passing untrusted text as the format. Calling
printf($userInput)treats any%in the input as a directive and can throwArgumentCountError. Writeprintf("%s", $userInput)instead. - Forgetting to escape a percent sign. A literal percent needs
%%. A single%begins a placeholder. - Expecting a string back.
printf()returns the length, not the text. Reach forsprintf()when you want to store, return or escape the result. - Supplying too few arguments. Every placeholder needs a value, except
%%. - Escaping
$incorrectly. In double-quoted strings%1$scan be interpreted as a variable. Use%1\$sor single quotes. - Rounding surprises.
%.2frounds for display only. It does not change the stored value and cannot fix floating-point representation issues.
Related functions
sprintf()returns the formatted string instead of printing it.vprintf()andvsprintf()take the values as an array.fprintf()andvfprintf()write to a stream.number_format()groups thousands and chooses separators.printandechooutput strings without formatting.sscanf()parses a string according to a format, the reverse direction.
Recap
printf() prints a template filled with formatted values and returns the number of characters it printed. Learn the placeholder shape %[argnum$][flags][width][.precision]specifier, escape literal percent signs as %%, never use untrusted input as the template, and switch to sprintf() when you need the formatted text as a value.
Tested examples
$length = printf("%s has %d items\n", "Cart", 3);
echo $length, "\n";
Cart has 3 items 17
$rows = [["Pen", 1.5, 3], ["Notebook", 12.25, 10]];
foreach ($rows as [$name, $price, $qty]) {
printf("%-10s|%8.2f|%03d\n", $name, $price, $qty);
}
Pen | 1.50|003 Notebook | 12.25|010
printf("%2\$s scored %1\$d%% (%3\$s)\n", 87, "Ana", "pass");
printf("#%02X%02X%02X\n", 255, 128, 0);
printf("[%'*8s]\n", "php");
printf("[%5.1s]\n", "hello");
Ana scored 87% (pass) #FF8000 [*****php] [ h]