VMware ESXi and vSphere Cluster Management

Convert Tabs to Spaces in Linux with expand

Learn how to replace tab characters with spaces in Linux using expand, choose tab widths, verify whitespace, and safely replace the original file.

Why convert tabs to spaces?

A tab character is a horizontal whitespace control character, commonly represented as \t. When displayed, it moves the cursor to the next tab stop, which is a column position used to determine how wide the tab appears.

A space character is one literal blank printable character. Unlike a tab, its width is always one character. The displayed width of a tab can vary between terminals, editors, printers, and programs because they may use different tab-stop settings.

Converting tabs to spaces can make layout more predictable when printing, sharing plain-text files, or using tools that require spaces. It is important to distinguish two operations:

  • Literal replacement: replace each tab with exactly one space.
  • Tab expansion: replace each tab with enough spaces to reach the next tab stop, preserving column alignment.

For example, a tab near the beginning of a line might become four spaces when the next tab stop is column 5, but a tab later in the line might become only two spaces. Tab expansion depends on the current column.

The expand command

expand is a standard Linux and Unix command-line utility for converting tabs in text input into spaces. It can read from a named file or from standard input, the input stream supplied by a pipe or the terminal. It writes converted text to standard output, the normal output stream for a command.

expand does not automatically modify the source file. Unless output is redirected, the converted text is printed in the terminal.

Basic conversion workflow

Print converted text

Give expand a filename to convert its contents and print the result:

expand input.txt

The original input.txt remains unchanged. This is useful for a quick preview.

Save the result in another file

Use shell output redirection with > to write standard output to a separate destination:

expand input.txt > output.txt

With the default tab-stop behavior, each tab becomes the number of spaces needed to reach the next default tab stop. Inspect the generated file with a command such as:

cat output.txt

For a more useful whitespace check, use cat -te or sed -n 'l', as described below.

Choosing tab stops with -t

The -t option, also written as --tabs, selects tab stops or a tab width. A single value specifies regularly spaced tab stops. For example, -t 4 uses positions based on four-column intervals.

OptionMeaningEffect on a tabTypical use
-t 1Use one-column tab stopsEvery tab becomes exactly one spaceFiles where tabs separate fields and one blank is wanted
-t 4Use four-column tab stopsEach tab expands to enough spaces to reach the next four-column boundaryFour-space indentation or four-column text layouts
-t 8 or default behaviorUse eight-column tab stopsTabs expand according to conventional eight-column stopsGeneral text and files created with common terminal settings
Custom tab-stop listUse explicit column positions, supplied as a comma-separated listEach tab advances to the next listed positionReports or files with irregular fixed columns

Replace every tab with one space

Use -t 1 when the goal is specifically one literal space per tab:

expand -t 1 input.txt > output.txt

This does not preserve table alignment based on wider stops. A line containing several tab-separated fields will simply contain one space for each tab.

Preserve four-column alignment

For source-like text or a layout intended to use four-column tab positions, use:

expand -t 4 input.txt > output.txt

Here, a tab does not always become four spaces. It becomes enough spaces to reach the next four-column boundary from the current position.

Use custom tab stops

Some reports need specific columns rather than regularly repeating stops. A comma-separated list supplies explicit positions. For example:

expand -t 5,12, twenty input.txt > output.txt

Use numeric positions appropriate for the file and verify the exact syntax supported by the local implementation. The local manual is authoritative:

man expand

On typical GNU systems, a list such as -t 5,12,20 defines successive tab-stop positions. Avoid spaces inside the option value.

Process input from a pipe

When no input filename is supplied, expand can read standard input. This makes it useful in pipelines:

printf 'name\trole\n' | expand -t 1

The pipeline emits:

name role

The first command produces text containing a tab and a newline. expand converts the tab before writing the result to standard output.

Safely replace the original file

Do not redirect output directly to the same path that expand is reading:

expand input.txt > input.txt

When the shell opens the redirection target, it can truncate the file before expand reads it. The source may therefore become empty or damaged.

Write to a new file first, inspect it, and replace the original only after verification:

expand -t 1 input.txt > input.txt.new

After checking the result, move the new file into place:

mv input.txt.new input.txt

A temporary file provides the same basic safety pattern and is especially useful in scripts. For an automated replacement after successful conversion, use:

expand -t 1 input.txt > input.txt.new && mv input.txt.new input.txt

The && operator runs mv only if expand exits successfully. Review or back up important files before replacing them.

ApproachExampleResultRecommendation
Write to a new fileexpand input.txt > output.txtOriginal and converted files both remainGood for review and comparison
Write to a temporary file, then move itexpand input.txt > input.txt.new && mv input.txt.new input.txtOriginal is replaced only after conversion succeedsPreferred for a controlled in-place replacement
Redirect directly to the input filenameexpand input.txt > input.txtInput may be truncated before it is readUnsafe; do not use

Make invisible whitespace visible

Normal terminal output can make a tab and several spaces look similar. Use cat -te to display tabs as ^I and line endings as $:

cat -te input.txt
cat -te output.txt

You can also use sed -n 'l', which displays nonprinting characters in an escaped form:

sed -n 'l' input.txt
sed -n 'l' output.txt

Compare the original and converted files with a side-by-side or difference tool when needed:

diff -u input.txt output.txt

A difference view will show changed whitespace, but remember that an ordinary visual inspection may not reveal the difference. Check formatting-sensitive files before replacing them.

Troubleshooting

The converted file looks unchanged

Tabs and spaces may both render as blank areas. Inspect both files with cat -te or sed -n 'l'. Remaining ^I markers indicate tabs are still present.

Columns no longer line up

If you used -t 1, every tab became one space. That is correct for literal replacement but not for tables. Rerun the conversion with a suitable width such as:

expand -t 4 input.txt > output.txt
expand -t 8 input.txt > output.txt

The source file became empty or damaged

The likely cause is redirecting output to the input filename. Restore the file from a backup if necessary. In future, write to a separate temporary or new file and move it only after validation.

expand is not found

Check whether the utility is available on the command search path:

command -v expand

If no path is returned, install or enable the standard GNU or core text utilities package appropriate for the Linux distribution and environment.

Spacing is unexpected near line starts or fields

The selected tab-stop setting may not match the assumptions used to create the file. Display the tabs, determine the intended columns, and rerun expand with the matching -t value or a custom tab-stop list.

Exam-relevant points

  • expand converts tabs to spaces; it does not convert spaces to tabs.
  • Without redirection, converted data goes to standard output and the source file is not modified.
  • -t 1 makes each tab one space.
  • A wider setting such as -t 4 or -t 8 expands tabs to the next matching tab stop and may produce different numbers of spaces on different lines.
  • Never use > with the same input and output filename unless a tool explicitly supports safe in-place editing.
  • Use cat -te or sed -n 'l' when whitespace is invisible.