Using Bash printf Command for Printing Formatted Outputs

You may print simple outputs with echo command but that's not enough for complicated formatted outputs.

Abhishek Prakash
Abhishek Prakash

Table of Contents

The simplest way to print in Linux command line is by using echo command.

echo "Value of var is $var"

However, echo command won't be adequate when you need to print formatted output.

This is where printf command helps you. The bash printf command operates like the printf command in C/C++ programming language.

printf "My brother %s is %d years old.\n" Prakash 21

Can you guess the output?

Bash printf command example

The first argument %s expects a string, %d expects a decimal integer, just like C/C++. Don't worry if you are not familiar with C/C++.

You don't need to learn it just for using printf command in your Bash scripts. Let me show you some examples of Bash printf command.

Using Bash printf command

Let's start with the syntax first.

printf format [arguments]

Here, format is a string that determines how the subsequent values will be displayed.

In the example printf "My brother %s is %d years old.\n" Prakash 21, the entire "My brother %s is %d years old.\n" is format and it is followed by the arguments Prakash and 21. The arguments are used for replacing the format specifiers (%s, %d etc) which I'll explain later in this article.

In its simplest form, printf can be used as echo command for displaying a string.

printf "Hello World\n"

Notice the new line character \n at the end? The difference between echo and printf command is that echo automatically adds a new line character at the end but for printf, you have to explicitly add it.

echo vs printf

Pay special attention to type and number of arguments

Keep in mind that the format string tries to be applied to all the arguments. This is why you should pay special attention to it.

abhishek@handbook:~$ printf "Hello, %s! \n" Abhishek Prakash
Hello, Abhishek! 
Hello, Prakash!
Example of bash printf command

Similarly, you should also pay attention to the kind of format specifier it expects in the format string.

bash printf command examples

As you can see in the above example, if it doesn't find intended arguments, it displays the default values which is null for strings and 0 for integers.

printf "Hi %s, your room number is %d. \n" Abhishek Prakash 131
bash: printf: Prakash: invalid number
Hi Abhishek, your room number is 0. 
Hi 131, your room number is 0.

Here, it takes Abhishek Prakash as first set of arguments and 131 as second set of arguments.

When it finds a string (Prakash) instead of an integer, it complains but it continues to display the output with second argument at its default value 0.

Similarly, it sees 131 as string in the second set of arguments and since the second argument is absent, it defaults to 0.

Format specification characters

There are several format specifiers available for you to display your output in desired format. Here are some of the most common ones:

Character Usage
%s String
%c Single character
%d Integers
%o Octal integers
%x Hexadecimal integers
%f Floating point
%b String with backslash escape character
%% Percent sign

Now that you are familiar with the format specifier, let's see some more examples that shows them in action.

Bash printf command examples

I don't think you need detailed explanation for most of these examples as they are self-explanatory.

abhishek@handbook:~$ printf "The octal value of %d is %o\n" 30 30
The octal value of 30 is 36

Let's see the use of the %b specifier for correctly interpreting the backslash escaped character.

abhishek@handbook:~$ printf "String with backslash: %s\n" "Hello\nWorld!"
String with backslash: Hello\nWorld!

You see for %s, it makes no difference. But with %b the new line escape character will be correctly interpreted:

abhishek@handbook:~$ printf "String with backslash: %b\n" "Hello\nWorld!"
String with backslash: Hello

When you use the %c, it reads only character at a time.

abhishek@handbook:~$ printf "Character: %c\n" a
Character: a
abhishek@handbook:~$ printf "Character: %c\n" a b c
Character: a
Character: b
Character: c
abhishek@handbook:~$ printf "Character: %c\n" abc
Character: a

Using modifiers to display printf output in specific style

There are modifiers to change the look of the output as per your liking.

# modifier for octal and hexadecimal numbers

Earlier you saw the use of %o for converting decimal to octal. However, it wasn't very clear that it was an octal number. You can use the # modifier to display octal and hexadecimal numbers in proper format.

abhishek@handbook:~$ printf "%d is %#o in octal and %#x in hexadecimal\n" 30 30 30
30 is 036 in octal and 0x1e in hexadecimal

Space modifier for positive integers

You can use a space between % and d in %d to display a positive integer with a leading space. This helps when you have a column of positive and negative numbers. See which one looks more 'pretty':

abhishek@handbook:~$ printf "%d \n%d \n%d \n" 10 -10 10
abhishek@handbook:~$ printf "% d \n%d \n% d \n" 10 -10 10

Width modifier

The width modifier is a integer that specifies the minimum field width of the argument.

By default, it is right aligned:

abhishek@handbook:~$ printf "%10s| %5d\n" Age 23
       Age|    23

You can make it left aligned by adding - flag to it:

abhishek@handbook:~$ printf "%-10s| %-5d\n" Age 23
Age       | 23

Precision modifier

You can use the precision modifier (.) dot to specify a minimum number of digits to be displayed with %d, %u, %o, %x. It adds zero padding on the left of the value.

abhishek@handbook:~$ printf "Roll Number: %.5d\n" 23
Roll Number: 00023

If you use the precision modifier with a string, it specifies the maximum length of the string. If the string is longer, it gets truncated in the display.

abhishek@handbook:~$ printf "Name: %.4s\n" Abhishek
Name: Abhi

You may combine both width and precision modifier:

abhishek@handbook:~$ printf "Name: %.4s\n" Abhishek
Name: Abhi
abhishek@handbook:~$ printf "Name: %10.4s\n" Abhishek
Name:       Abhi

Bonus Example: Display output in tabular format with printf

Let's put what you have learned about printf command to some good use with a slightly more complicated example. This will showcase the true potential of the printf command in bash scripts.

Let's use printf command to print the following table using bash:

Name ID Age Grades
Sherlock Holmes 0000122 23 A
James Bond 0000007 27 F
Hercules Poirot 0006811 59 G
Jane Marple 1234567 71 C

Here's the shell script I wrote for this task. Your script may vary:

rows="%-15s| %.7d| %3d| %c\n"

printf "%-15s| %-7s| %.3s| %s\n" Name ID Age Grades
printf "%.${TableWidth}s\n" "$seperator"
printf "$rows" "Sherlock Holmes" 122 23 A
printf "$rows" "James Bond" 7 27 F
printf "$rows" "Hercules Poirot" 6811 59 G
printf "$rows" "Jane Marple" 1234567 71 C

Now if I run this bash shell script, here's what it prints:

Isn't it wonderful to use the bash printf command to print beautifully formatted output for your scripts?

I hope you liked this detailed tutorial on the printf command in Linux. If you have questions or suggestions, please let me know. And don't forget to become a member of Linux Handbook for more such informational Linux learnings.

Join the conversation.