In this project we will implement a printf() function of the following prototype: int _printf(const char *format, ...);
The function is variadic and thus takes any amount of arguments following the format pointer.
- Implement custom printf() function similar to that of the standard library
- Use variadic functions to allow a custom number of arguments
- Parse a format string to identify custom print options
Use - General:_printf("format string", var1, var2, ...);
Examples:
-
Basic String:
_printf("%s World", "Hello");- Output:
Hello World
- Output:
-
Print integers:
_printf("Here is an array element: arr[%d]:%c", 32, arr[32]);- Output:
Here is an array element arr[32]:A
- Output:
You can do much more, by combining specifiers like string or integer (full list of specifiers below) with flags, length modifiers, width, and precision.
Return value of _printf()
_printf() returns negative one (-1) upon failure, and the number of bytes (as an int) written to standard output upon success.
Format specifiers follow this pattern: %[flags][width][.precision][length]specifier
- Example:
_printf("%+.22ld\n", LONG_MAX)- Output:
+0009223372036854775807
- Output:
The specifier character at the end is the most significant component, since it defines the type and the interpretation of its corresponding argument:
| Specifier | Output | Examples |
|---|---|---|
d or i |
Signed integer | 1024, -1024 |
u |
Unsigned integer | 1024 |
o |
Unsigned octal | 432 |
x |
Unsigned hexadecimal integer | 3ca |
X |
Unsigned hexadecimal integer (uppercase) | 3CA |
b |
Binary Representation of unsigned integer | 01010110 |
p |
Pointer address | 0x403212 |
s |
String of characters | Hello World |
c |
Character | y |
r |
Reversed string of characters | dlroW olleH |
R |
ROT13 Translation of string | Uryyb |
S |
String with hex-ascii value replacing special chars | \x0A\x0A |
| The format specifier can also contain sub-specifiers: flags, width, .precision and modifiers (in that order), which are optional and follow these specifications: |
| Flag | Description |
|---|---|
- |
Left-justify the output within the field width that was given; Right justification is the default (see width sub-specifier). |
+ |
Preceeds the result with a plus or minus sign (+ or -) even for positive numbers. By default, only negative numbers are preceded with a - sign. |
(space) |
If no sign is going to be written, a blank space is inserted before the value. |
# |
Used with o, x or X specifiers the value is preceeded with 0, 0x or 0X respectively for values different than zero. |
0 |
Left-pads the number with zeroes (0) instead of spaces when padding is specified (see width sub-specifier). |
| Width | Description |
|---|---|
(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. |
* |
The width is not specified in the format string, but as an additional integer value argument preceding the argument that has to be formatted. |
| .Precision | Description |
|---|---|
.(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 s: this is the maximum number of characters to be printed. By default all characters are printed until the ending null character is encountered. If the period is specified without an explicit value for precision, 0 is assumed. |
.* |
The precision is not specified in the format string, but as an additional integer value argument preceding the argument that has to be formatted. |
The length sub-specifier modifies the length of the data type. This is a chart showing the types used to interpret the corresponding arguments with and without length specifier (if a different type is used, the proper type promotion or conversion is performed, if allowed
| Modifier/Specifier | d & i |
u, o, x, X |
c |
s |
p |
|---|---|---|---|---|---|
none |
int | unsigned int | int | char pointer | void pointer |
h |
short int | unsigned short int | |||
l |
long int | unsigned long int |
All together they allow you to manipulate output for various formatting techniques. Although printf does essentially the same thing, we have replicated it to further deepen our understanding of C.
- “Printf.” Cplusplus.com, www.cplusplus.com/reference/cstdio/printf/.
