Seeing Odd Behavior from printf

Problem

Your script is giving you values that don’t match what you expected. Consider this simple script and its output:

$ bash oddscript
good nodes: 0
bad nodes: 6
miss nodes: 0
GOOD=6 BAD=0 MISS=0
$
$ cat oddscript
#!/bin/bash -
badnode=6

printf "good nodes: %d\n" $goodnode
printf "bad nodes: %d\n" $badnode
printf "miss nodes: %d\n" $missnode
printf "GOOD=%d BAD=%d MISS=%d\n" $goodnode $badnode $missnode

Why is 6 showing up as the value for the good count, when it is supposed to be the value for the bad count?

Solution

Either give the variables an initial value (e.g., 0) or put quotes around the references to them on printf lines.

Discussion

What’s happening here? bash does its substitutions on that last line and when it evaluates $goodnode and $missnode they both come out null, empty, not there. So the line that is handed off to printf to execute looks like this:

printf "GOOD=%d BAD=%d MISS=%d\n" 6

When printf tries to print the three decimal values (the three %d formats) it has a value (i.e., 6) for the first one, but doesn’t have anything for the next two, so they come out zero and we get:

GOOD=6 BAD=0 MISS=0

You can’t really blame printf, since it never saw the other arguments; bash had done its parameter substitution before printf ever got to run.

Even declaring them as integer values, like this:

declare -i goodnode badnode missnode

isn’t enough. You need to actually assign them a value.

The other way to avoid this problem is to quote the arguments when they ...

Get bash Cookbook now with the O’Reilly learning platform.

O’Reilly members experience books, live events, courses curated by job role, and more from O’Reilly and nearly 200 top publishers.