Skip to content
VLSI Mentor

Tcl Part I · Module 5 · Strings

format: Producing Output You Can Line Up

Two problems come up constantly in any script that produces output for a person to read: making columns line up, and showing a number to a sensible number of decimal places. This command solves both, and it is worth learning properly rather than copying patterns, because the syntax has a simple structure underneath it. A conversion is four optional parts in a fixed order, and once you can see that structure you can write any conversion you need instead of recognising the four you have seen before.

Foundation13 min readTclPart IStringsformatOutput

Part I · Module 5 · Chapter 5.11 · format: Producing Output You Can Line Up

1. The Shape

Azvya Education Pvt. Ltd.VLSI Mentor
basic.tcl
puts [format "name: %s  count: %d" "widget" 42]
Azvya Education Pvt. Ltd.VLSI Mentor
Snippet
name: widget  count: 42

The first argument is a format string: literal text with conversions marked by %. The remaining arguments fill those conversions, in order.

Everything that is not a conversion is copied through exactly.

2. The Common Types

Azvya Education Pvt. Ltd.VLSI Mentor
types.tcl
puts [format "%s" "text"]
puts [format "%d" 42]
puts [format "%f" 3.5]
puts [format "%e" 12345.678]
puts [format "%x and %X" 255 255]
puts [format "%o" 8]
puts [format "%c" 65]
puts [format "100%%"]
Azvya Education Pvt. Ltd.VLSI Mentor
Snippet
text
42
3.500000
3.500000e+00
ff and FF
10
A
100%
ConversionProduces
%sthe value as text
%da whole number
%fa real number, six decimal places by default
%escientific notation
%x %Xhexadecimal, lower or upper case
%ooctal
%cthe character with that code
%%a literal percent sign

Note %f gave 3.500000. Six decimal places is the default and is almost never what you want, which is §4.

3. Width and Alignment

A number after the % sets a minimum width:

Azvya Education Pvt. Ltd.VLSI Mentor
width.tcl
puts [format "|%10s|" "right"]
puts [format "|%-10s|" "left"]
puts [format "|%10d|" 42]
Azvya Education Pvt. Ltd.VLSI Mentor
Snippet
|     right|
|left      |
|        42|

Right-aligned by default; a minus sign aligns left. The width is a minimum — longer values are not truncated.

This is what makes a table:

Azvya Education Pvt. Ltd.VLSI Mentor
table.tcl
puts [format "%-14s %8s" "SIGNAL" "WIDTH"]
puts [format "%-14s %8s" "--------------" "--------"]

foreach {name width} {clk 1 reset 1 data_valid 1 payload 64} {
    puts [format "%-14s %8d" $name $width]
}
Azvya Education Pvt. Ltd.VLSI Mentor
Snippet
SIGNAL            WIDTH
-------------- --------
clk                   1
reset                 1
data_valid            1
payload              64

Names left-aligned in 14 characters, numbers right-aligned in 8. That is the whole technique, and it replaces the manual padding of Chapter 5.2 §6.

4. Decimal Places

A dot and a number set the precision:

Azvya Education Pvt. Ltd.VLSI Mentor
precision.tcl
puts [format "%f"    3.14159]
puts [format "%.2f"  3.14159]
puts [format "%.0f"  3.14159]
puts [format "%8.3f" 3.14159]
Azvya Education Pvt. Ltd.VLSI Mentor
Snippet
3.141590
3.14
3
   3.142

%.2f is the one you will use most. It is the correct answer to "round this for display", which Chapter 4.8 §5 and Chapter 4.10 §7 both deferred to this chapter.

With %s, precision truncates instead:

Azvya Education Pvt. Ltd.VLSI Mentor
truncate.tcl
puts [format "%.5s" "truncated"]
Azvya Education Pvt. Ltd.VLSI Mentor
Snippet
trunc

5. Flags

The optional characters right after %:

Azvya Education Pvt. Ltd.VLSI Mentor
flags.tcl
puts [format "%05d"  42]
puts [format "%+d %+d" 5 -5]
puts [format "%-8d|" 42]
puts [format "% d" 42]
Azvya Education Pvt. Ltd.VLSI Mentor
Snippet
00042
+5 -5
42      |
 42
FlagEffect
-align left
0pad with zeros instead of spaces
+always show a sign
spaceshow a space where a plus would be

%05d is how you produce a zero-padded identifier — 00042.

6. The Full Structure

Putting it together, a conversion has four optional parts in a fixed order:

Azvya Education Pvt. Ltd.VLSI Mentor
Snippet
%  -0+     10      .3       f
   │       │       │        │
   │       │       │        └── type       (required)
   │       │       └─────────── precision  (optional)
   │       └─────────────────── width      (optional)
   └─────────────────────────── flags      (optional)
Azvya Education Pvt. Ltd.VLSI Mentor
full.tcl
puts [format "|%-10.3f|" 3.14159]
puts [format "|%+08.2f|" 3.14159]
Azvya Education Pvt. Ltd.VLSI Mentor
Snippet
|3.142     |
|+0003.14|

Read any conversion left to right in that order and it stops being cryptic.

7. Width From a Variable

A * takes the width from an argument:

Azvya Education Pvt. Ltd.VLSI Mentor
star.tcl
set w 6
puts [format "|%*d|" $w 42]
Azvya Education Pvt. Ltd.VLSI Mentor
Snippet
|    42|

Useful when the column width is computed — for instance from the longest name in a list.

8. Common Mistakes

Wrong number of arguments. Each conversion consumes one, so a stray % shifts everything after it.

Using %d on a real number. It is an error, not a truncation. Convert with int() first.

Forgetting %% for a literal percent. A lone % followed by a letter is read as a conversion.

Using %f without a precision. Six decimal places is rarely what you meant. §2.

Expecting width to truncate. It is a minimum. Use a precision with %s to cut text. §4.

Reading back a %05d value as a number. It is octal. §5.

9. Exercises

Exercise 1 — the types. Produce, from the value 255: the decimal form, lowercase hex, uppercase hex, and octal.

Exercise 2 — a table. Print a three-column table of name, count and percentage for four rows, with names left-aligned in 12 characters, counts right-aligned in 6, and percentages to one decimal place.

Exercise 3 — zero padding. Produce 007, 0042 and 00000. Then read 007 back with expr and explain the result.

Exercise 4 — read the conversion. Without running, say what each produces for the value 3.14159: %6.2f, %-6.2f, %+.4f, %08.1f.

Exercise 5 — percent sign. Print completed: 75% where the 75 comes from a variable.

Exercise 6 — compute the width. Given the names {clk reset data_valid}, find the longest with string length, then use %*s to print all three in a column exactly that wide.

10. Remember

  • A format string is literal text plus conversions, and each conversion consumes one argument.
  • Types: %s %d %f %e %x %o %c, and %% for a literal percent.
  • A number is a minimum width, right-aligned; - aligns left.
  • A dot and a number set precision — decimal places for %f, truncation for %s.
  • %.2f is the right way to round for display. It produces text and does not change the value.
  • Flags are - 0 + and space, and %05d gives zero padding.
  • The order is flags, width, precision, type.
  • * takes the width from an argument.
  • A zero-padded number read back by expr is octal.

Next: taking a formatted line apart again.

Where this fits

Part of the Tcl curriculum.